prevent nic removal on out of bounds router stop (#8371)
Co-authored-by: Vishesh <vishesh92@gmail.com>
Co-authored-by: Wei Zhou <weizhou@apache.org>
diff --git a/api/src/main/java/com/cloud/vm/NicProfile.java b/api/src/main/java/com/cloud/vm/NicProfile.java
index 3f37331..d3c1daa 100644
--- a/api/src/main/java/com/cloud/vm/NicProfile.java
+++ b/api/src/main/java/com/cloud/vm/NicProfile.java
@@ -442,6 +442,6 @@
@Override
public String toString() {
- return String.format("NicProfile %s", ReflectionToStringBuilderUtils.reflectOnlySelectedFields(this, "id", "vmId", "reservationId", "iPv4Address", "broadcastUri"));
+ return String.format("NicProfile %s", ReflectionToStringBuilderUtils.reflectOnlySelectedFields(this, "id", "vmId", "deviceId", "broadcastUri", "reservationId", "iPv4Address"));
}
}
diff --git a/core/src/main/java/com/cloud/serializer/GsonHelper.java b/core/src/main/java/com/cloud/serializer/GsonHelper.java
index 7ac85d3..7c33ef0 100644
--- a/core/src/main/java/com/cloud/serializer/GsonHelper.java
+++ b/core/src/main/java/com/cloud/serializer/GsonHelper.java
@@ -51,6 +51,8 @@
GsonBuilder loggerBuilder = new GsonBuilder();
loggerBuilder.disableHtmlEscaping();
loggerBuilder.setExclusionStrategies(new LoggingExclusionStrategy(s_logger));
+ loggerBuilder.serializeSpecialFloatingPointValues();
+ // maybe add loggerBuilder.serializeNulls(); as well?
s_gogger = setDefaultGsonConfig(loggerBuilder);
s_logger.info("Default Builder inited.");
}
diff --git a/engine/orchestration/src/main/java/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java b/engine/orchestration/src/main/java/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java
index 6c10a02..57f6f99 100644
--- a/engine/orchestration/src/main/java/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java
+++ b/engine/orchestration/src/main/java/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java
@@ -2310,12 +2310,12 @@
@DB
protected void releaseNic(final VirtualMachineProfile vmProfile, final long nicId) throws ConcurrentOperationException, ResourceUnavailableException {
- final Pair<Network, NicProfile> networkToRelease = Transaction.execute(new TransactionCallback<Pair<Network, NicProfile>>() {
+ final Pair<Network, NicProfile> networkToRelease = Transaction.execute(new TransactionCallback<>() {
@Override
public Pair<Network, NicProfile> doInTransaction(final TransactionStatus status) {
final NicVO nic = _nicDao.lockRow(nicId, true);
if (nic == null) {
- throw new ConcurrentOperationException("Unable to acquire lock on nic " + nic);
+ throw new ConcurrentOperationException(String.format("Unable to acquire lock on nic id=%d", nicId));
}
final Nic.State originalState = nic.getState();
@@ -2329,6 +2329,9 @@
final NicProfile profile = new NicProfile(nic, network, nic.getBroadcastUri(), nic.getIsolationUri(), null, _networkModel
.isSecurityGroupSupportedInNetwork(network), _networkModel.getNetworkTag(vmProfile.getHypervisorType(), network));
if (guru.release(profile, vmProfile, nic.getReservationId())) {
+ if (s_logger.isDebugEnabled()) {
+ s_logger.debug(String.format("The nic %s on %s was released according to %s by guru %s, now updating record.", nic, profile, vmProfile, guru));
+ }
applyProfileToNicForRelease(nic, profile);
nic.setState(Nic.State.Allocated);
if (originalState == Nic.State.Reserved) {
@@ -2338,7 +2341,7 @@
}
}
// Perform release on network elements
- return new Pair<Network, NicProfile>(network, profile);
+ return new Pair<>(network, profile);
} else {
nic.setState(Nic.State.Allocated);
updateNic(nic, network.getId(), -1);
@@ -2435,7 +2438,7 @@
for (final NetworkElement element : networkElements) {
if (providersToImplement.contains(element.getProvider())) {
if (s_logger.isDebugEnabled()) {
- s_logger.debug("Asking " + element.getName() + " to release " + nic);
+ s_logger.debug(String.format("Asking %s to release %s, according to the reservation strategy %s", element.getName(), nic, nic.getReservationStrategy()));
}
try {
element.release(network, profile, vm, null);
diff --git a/engine/schema/src/main/java/com/cloud/vm/NicVO.java b/engine/schema/src/main/java/com/cloud/vm/NicVO.java
index a32a943..936efd1 100644
--- a/engine/schema/src/main/java/com/cloud/vm/NicVO.java
+++ b/engine/schema/src/main/java/com/cloud/vm/NicVO.java
@@ -30,6 +30,7 @@
import javax.persistence.Table;
import javax.persistence.Transient;
+import org.apache.cloudstack.utils.reflectiontostringbuilderutils.ReflectionToStringBuilderUtils;
import org.apache.commons.lang3.builder.EqualsBuilder;
import org.apache.commons.lang3.builder.HashCodeBuilder;
@@ -329,17 +330,7 @@
@Override
public String toString() {
- return new StringBuilder("Nic[").append(id)
- .append("-")
- .append(instanceId)
- .append("-")
- .append(deviceId)
- .append("-")
- .append(reservationId)
- .append("-")
- .append(iPv4Address)
- .append("]")
- .toString();
+ return String.format("Nic %s", ReflectionToStringBuilderUtils.reflectOnlySelectedFields(this, "id", "instanceId", "deviceId", "broadcastUri", "reservationId", "iPv4Address"));
}
@Override
diff --git a/server/src/main/java/com/cloud/network/guru/ControlNetworkGuru.java b/server/src/main/java/com/cloud/network/guru/ControlNetworkGuru.java
index ce62c7b..ce59b50 100644
--- a/server/src/main/java/com/cloud/network/guru/ControlNetworkGuru.java
+++ b/server/src/main/java/com/cloud/network/guru/ControlNetworkGuru.java
@@ -21,6 +21,7 @@
import javax.inject.Inject;
import javax.naming.ConfigurationException;
+import com.cloud.network.router.VirtualNetworkApplianceManager;
import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
import org.apache.log4j.Logger;
@@ -166,18 +167,24 @@
assert nic.getTrafficType() == TrafficType.Control;
HypervisorType hType = vm.getHypervisorType();
if ( ( (hType == HypervisorType.VMware) || (hType == HypervisorType.Hyperv) )&& isRouterVm(vm)) {
+ if (!VirtualNetworkApplianceManager.RemoveControlIpOnStop.valueIn(vm.getVirtualMachine().getDataCenterId())) {
+ if (s_logger.isDebugEnabled()) {
+ s_logger.debug(String.format("not releasing %s from %s with reservationId %s, as systemvm.release.control.ip.on.stop is set to false for the data center.", nic, vm, reservationId));
+ }
+ return true;
+ }
long dcId = vm.getVirtualMachine().getDataCenterId();
DataCenterVO dcVo = _dcDao.findById(dcId);
if (dcVo.getNetworkType() != NetworkType.Basic) {
super.release(nic, vm, reservationId);
if (s_logger.isDebugEnabled()) {
- s_logger.debug("Released nic: " + nic);
+ s_logger.debug(String.format("Released nic: %s for vm %s", nic, vm));
}
return true;
} else {
nic.deallocate();
if (s_logger.isDebugEnabled()) {
- s_logger.debug("Released nic: " + nic);
+ s_logger.debug(String.format("Released nic: %s for vm %s", nic, vm));
}
return true;
}
@@ -187,7 +194,7 @@
nic.deallocate();
if (s_logger.isDebugEnabled()) {
- s_logger.debug("Released nic: " + nic);
+ s_logger.debug(String.format("Released nic: %s for vm %s", nic, vm));
}
return true;
diff --git a/server/src/main/java/com/cloud/network/guru/PodBasedNetworkGuru.java b/server/src/main/java/com/cloud/network/guru/PodBasedNetworkGuru.java
index 9f9771e..44d349a 100644
--- a/server/src/main/java/com/cloud/network/guru/PodBasedNetworkGuru.java
+++ b/server/src/main/java/com/cloud/network/guru/PodBasedNetworkGuru.java
@@ -159,7 +159,7 @@
nic.deallocate();
if (s_logger.isDebugEnabled()) {
- s_logger.debug("Released nic: " + nic);
+ s_logger.debug(String.format("Released nic: %s for vm %s", nic, vm));
}
return true;
diff --git a/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManager.java b/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManager.java
index 8b2fd81..387e505 100644
--- a/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManager.java
+++ b/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManager.java
@@ -36,82 +36,83 @@
*/
public interface VirtualNetworkApplianceManager extends Manager, VirtualNetworkApplianceService {
- static final String RouterTemplateXenCK = "router.template.xenserver";
- static final String RouterTemplateKvmCK = "router.template.kvm";
- static final String RouterTemplateVmwareCK = "router.template.vmware";
- static final String RouterTemplateHyperVCK = "router.template.hyperv";
- static final String RouterTemplateLxcCK = "router.template.lxc";
- static final String RouterTemplateOvm3CK = "router.template.ovm3";
- static final String SetServiceMonitorCK = "network.router.EnableServiceMonitoring";
- static final String RouterAlertsCheckIntervalCK = "router.alerts.check.interval";
- static final String VirtualRouterServiceOfferingCK = "router.service.offering";
+ String RouterTemplateXenCK = "router.template.xenserver";
+ String RouterTemplateKvmCK = "router.template.kvm";
+ String RouterTemplateVmwareCK = "router.template.vmware";
+ String RouterTemplateHyperVCK = "router.template.hyperv";
+ String RouterTemplateLxcCK = "router.template.lxc";
+ String RouterTemplateOvm3CK = "router.template.ovm3";
+ String SetServiceMonitorCK = "network.router.EnableServiceMonitoring";
+ String RouterAlertsCheckIntervalCK = "router.alerts.check.interval";
+ String VirtualRouterServiceOfferingCK = "router.service.offering";
- static final String RouterHealthChecksConfigRefreshIntervalCK = "router.health.checks.config.refresh.interval";
- static final String RouterHealthChecksResultFetchIntervalCK = "router.health.checks.results.fetch.interval";
- static final String RouterHealthChecksFailuresToRecreateVrCK = "router.health.checks.failures.to.recreate.vr";
+ String RouterHealthChecksConfigRefreshIntervalCK = "router.health.checks.config.refresh.interval";
+ String RouterHealthChecksResultFetchIntervalCK = "router.health.checks.results.fetch.interval";
+ String RouterHealthChecksFailuresToRecreateVrCK = "router.health.checks.failures.to.recreate.vr";
+ String RemoveControlIpOnStopCK = "systemvm.release.control.ip.on.stop";
- static final ConfigKey<String> RouterTemplateXen = new ConfigKey<String>(String.class, RouterTemplateXenCK, "Advanced", "SystemVM Template (XenServer)",
+ ConfigKey<String> RouterTemplateXen = new ConfigKey<>(String.class, RouterTemplateXenCK, "Advanced", "SystemVM Template (XenServer)",
"Name of the default router template on Xenserver.", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<String> RouterTemplateKvm = new ConfigKey<String>(String.class, RouterTemplateKvmCK, "Advanced", "SystemVM Template (KVM)",
+ ConfigKey<String> RouterTemplateKvm = new ConfigKey<>(String.class, RouterTemplateKvmCK, "Advanced", "SystemVM Template (KVM)",
"Name of the default router template on KVM.", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<String> RouterTemplateVmware = new ConfigKey<String>(String.class, RouterTemplateVmwareCK, "Advanced", "SystemVM Template (vSphere)",
+ ConfigKey<String> RouterTemplateVmware = new ConfigKey<>(String.class, RouterTemplateVmwareCK, "Advanced", "SystemVM Template (vSphere)",
"Name of the default router template on Vmware.", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<String> RouterTemplateHyperV = new ConfigKey<String>(String.class, RouterTemplateHyperVCK, "Advanced", "SystemVM Template (HyperV)",
+ ConfigKey<String> RouterTemplateHyperV = new ConfigKey<>(String.class, RouterTemplateHyperVCK, "Advanced", "SystemVM Template (HyperV)",
"Name of the default router template on Hyperv.", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<String> RouterTemplateLxc = new ConfigKey<String>(String.class, RouterTemplateLxcCK, "Advanced", "SystemVM Template (LXC)",
+ ConfigKey<String> RouterTemplateLxc = new ConfigKey<>(String.class, RouterTemplateLxcCK, "Advanced", "SystemVM Template (LXC)",
"Name of the default router template on LXC.", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<String> RouterTemplateOvm3 = new ConfigKey<String>(String.class, RouterTemplateOvm3CK, "Advanced", "SystemVM Template (Ovm3)",
+ ConfigKey<String> RouterTemplateOvm3 = new ConfigKey<>(String.class, RouterTemplateOvm3CK, "Advanced", "SystemVM Template (Ovm3)",
"Name of the default router template on Ovm3.", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<Boolean> SetServiceMonitor = new ConfigKey<Boolean>(Boolean.class, SetServiceMonitorCK, "Advanced", "true",
+ ConfigKey<Boolean> SetServiceMonitor = new ConfigKey<>(Boolean.class, SetServiceMonitorCK, "Advanced", "true",
"service monitoring in router enable/disable option, default true", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<Integer> RouterAlertsCheckInterval = new ConfigKey<Integer>(Integer.class, RouterAlertsCheckIntervalCK, "Advanced", "1800",
+ ConfigKey<Integer> RouterAlertsCheckInterval = new ConfigKey<>(Integer.class, RouterAlertsCheckIntervalCK, "Advanced", "1800",
"Interval (in seconds) to check for alerts in Virtual Router.", false, ConfigKey.Scope.Global, null);
- static final ConfigKey<Boolean> RouterVersionCheckEnabled = new ConfigKey<Boolean>("Advanced", Boolean.class, "router.version.check", "true",
+ ConfigKey<Boolean> RouterVersionCheckEnabled = new ConfigKey<>("Advanced", Boolean.class, "router.version.check", "true",
"If true, router minimum required version is checked before sending command", false);
- static final ConfigKey<Boolean> UseExternalDnsServers = new ConfigKey<Boolean>(Boolean.class, "use.external.dns", "Advanced", "false",
+ ConfigKey<Boolean> UseExternalDnsServers = new ConfigKey<>(Boolean.class, "use.external.dns", "Advanced", "false",
"Bypass internal dns, use external dns1 and dns2", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<Boolean> ExposeDnsAndBootpServer = new ConfigKey<Boolean>(Boolean.class, "expose.dns.externally", "Advanced", "true",
+ ConfigKey<Boolean> ExposeDnsAndBootpServer = new ConfigKey<>(Boolean.class, "expose.dns.externally", "Advanced", "true",
"open dns, dhcp and bootp on the public interface", true, ConfigKey.Scope.Zone, null);
- static final ConfigKey<String> VirtualRouterServiceOffering = new ConfigKey<String>(String.class, VirtualRouterServiceOfferingCK, "Advanced", "",
+ ConfigKey<String> VirtualRouterServiceOffering = new ConfigKey<>(String.class, VirtualRouterServiceOfferingCK, "Advanced", "",
"Uuid of the service offering used by virtual routers; if NULL - system offering will be used", true, ConfigKey.Scope.Account, null);
// Health checks
- static final ConfigKey<Boolean> RouterHealthChecksEnabled = new ConfigKey<Boolean>(Boolean.class, "router.health.checks.enabled", "Advanced", "true",
+ ConfigKey<Boolean> RouterHealthChecksEnabled = new ConfigKey<>(Boolean.class, "router.health.checks.enabled", "Advanced", "true",
"If true, router health checks are allowed to be executed and read. If false, all scheduled checks and API calls for on demand checks are disabled.",
true, ConfigKey.Scope.Global, null);
- static final ConfigKey<Integer> RouterHealthChecksBasicInterval = new ConfigKey<Integer>(Integer.class, "router.health.checks.basic.interval", "Advanced", "3",
+ ConfigKey<Integer> RouterHealthChecksBasicInterval = new ConfigKey<>(Integer.class, "router.health.checks.basic.interval", "Advanced", "3",
"Interval in minutes at which basic router health checks are performed. If set to 0, no tests are scheduled.",
true, ConfigKey.Scope.Global, null, RouterHealthChecksEnabled.key());
- static final ConfigKey<Integer> RouterHealthChecksAdvancedInterval = new ConfigKey<Integer>(Integer.class, "router.health.checks.advanced.interval", "Advanced", "10",
+ ConfigKey<Integer> RouterHealthChecksAdvancedInterval = new ConfigKey<>(Integer.class, "router.health.checks.advanced.interval", "Advanced", "10",
"Interval in minutes at which advanced router health checks are performed. If set to 0, no tests are scheduled.",
true, ConfigKey.Scope.Global, null, RouterHealthChecksEnabled.key());
- static final ConfigKey<Integer> RouterHealthChecksConfigRefreshInterval = new ConfigKey<Integer>(Integer.class, RouterHealthChecksConfigRefreshIntervalCK, "Advanced", "10",
+ ConfigKey<Integer> RouterHealthChecksConfigRefreshInterval = new ConfigKey<>(Integer.class, RouterHealthChecksConfigRefreshIntervalCK, "Advanced", "10",
"Interval in minutes at which router health checks config - such as scheduling intervals, excluded checks, etc is updated on virtual routers by the management server. This value should" +
" be sufficiently high (like 2x) from the router.health.checks.basic.interval and router.health.checks.advanced.interval so that there is time between new results generation and results generation for passed data.",
false, ConfigKey.Scope.Global, null, RouterHealthChecksEnabled.key());
- static final ConfigKey<Integer> RouterHealthChecksResultFetchInterval = new ConfigKey<Integer>(Integer.class, RouterHealthChecksResultFetchIntervalCK, "Advanced", "10",
+ ConfigKey<Integer> RouterHealthChecksResultFetchInterval = new ConfigKey<>(Integer.class, RouterHealthChecksResultFetchIntervalCK, "Advanced", "10",
"Interval in minutes at which router health checks results are fetched by management server. On each result fetch, management server evaluates need to recreate VR as per configuration of " + RouterHealthChecksFailuresToRecreateVrCK +
"This value should be sufficiently high (like 2x) from the router.health.checks.basic.interval and router.health.checks.advanced.interval so that there is time between new results generation and fetch.",
false, ConfigKey.Scope.Global, null, RouterHealthChecksEnabled.key());
- static final ConfigKey<String> RouterHealthChecksFailuresToRecreateVr = new ConfigKey<String>(String.class, RouterHealthChecksFailuresToRecreateVrCK, "Advanced", "",
+ ConfigKey<String> RouterHealthChecksFailuresToRecreateVr = new ConfigKey<>(String.class, RouterHealthChecksFailuresToRecreateVrCK, "Advanced", "",
"Health checks failures defined by this config are the checks that should cause router recreation. If empty the recreate is not attempted for any health check failure. Possible values are comma separated script names " +
"from systemvm’s /root/health_scripts/ (namely - cpu_usage_check.py, dhcp_check.py, disk_space_check.py, dns_check.py, gateways_check.py, haproxy_check.py, iptables_check.py, memory_usage_check.py, router_version_check.py), connectivity.test, filesystem.writable.test " +
" or services (namely - loadbalancing.service, webserver.service, dhcp.service) ",
true, ConfigKey.Scope.Zone, null, null, RouterHealthChecksEnabled.key(), null, null, ConfigKey.Kind.CSV, null);
- static final ConfigKey<String> RouterHealthChecksToExclude = new ConfigKey<String>(String.class, "router.health.checks.to.exclude", "Advanced", "",
+ ConfigKey<String> RouterHealthChecksToExclude = new ConfigKey<>(String.class, "router.health.checks.to.exclude", "Advanced", "",
"Health checks that should be excluded when executing scheduled checks on the router. This can be a comma separated list of script names placed in the '/root/health_checks/' folder. Currently the following scripts are " +
"placed in default systemvm template - cpu_usage_check.py, disk_space_check.py, gateways_check.py, iptables_check.py, router_version_check.py, dhcp_check.py, dns_check.py, haproxy_check.py, memory_usage_check.py.",
true, ConfigKey.Scope.Zone, null, null, RouterHealthChecksEnabled.key(), null, null, ConfigKey.Kind.CSV, null);
- static final ConfigKey<Double> RouterHealthChecksFreeDiskSpaceThreshold = new ConfigKey<Double>(Double.class, "router.health.checks.free.disk.space.threshold",
+ ConfigKey<Double> RouterHealthChecksFreeDiskSpaceThreshold = new ConfigKey<>(Double.class, "router.health.checks.free.disk.space.threshold",
"Advanced", "100", "Free disk space threshold (in MB) on VR below which the check is considered a failure.",
true, ConfigKey.Scope.Zone, null, RouterHealthChecksEnabled.key());
- static final ConfigKey<Double> RouterHealthChecksMaxCpuUsageThreshold = new ConfigKey<Double>(Double.class, "router.health.checks.max.cpu.usage.threshold",
+ ConfigKey<Double> RouterHealthChecksMaxCpuUsageThreshold = new ConfigKey<>(Double.class, "router.health.checks.max.cpu.usage.threshold",
"Advanced", "100", " Max CPU Usage threshold as % above which check is considered a failure.",
true, ConfigKey.Scope.Zone, null, RouterHealthChecksEnabled.key());
- static final ConfigKey<Double> RouterHealthChecksMaxMemoryUsageThreshold = new ConfigKey<Double>(Double.class, "router.health.checks.max.memory.usage.threshold",
+ ConfigKey<Double> RouterHealthChecksMaxMemoryUsageThreshold = new ConfigKey<>(Double.class, "router.health.checks.max.memory.usage.threshold",
"Advanced", "100", "Max Memory Usage threshold as % above which check is considered a failure.",
true, ConfigKey.Scope.Zone, null, RouterHealthChecksEnabled.key());
ConfigKey<String> RouterLogrotateFrequency = new ConfigKey<>(String.class, "router.logrotate.frequency", "Advanced", "*:00:00",
@@ -121,23 +122,15 @@
"reach the minimum size.",
true, ConfigKey.Scope.Zone, null);
- public static final int DEFAULT_ROUTER_VM_RAMSIZE = 256; // 256M
- public static final int DEFAULT_ROUTER_CPU_MHZ = 500; // 500 MHz
- public static final boolean USE_POD_VLAN = false;
- public static final int DEFAULT_PRIORITY = 100;
- public static final int DEFAULT_DELTA = 2;
+ ConfigKey<Boolean> RemoveControlIpOnStop = new ConfigKey<>(Boolean.class, RemoveControlIpOnStopCK, "Advanced", "true",
+ "on stopping routers and system VMs the IP will be released to preserve IPv4 space.", true, ConfigKey.Scope.Zone, null);
- /**
- /*
- * Send ssh public/private key pair to specified host
- * @param hostId
- * @param pubKey
- * @param prvKey
- *
- * NOT USED IN THE VIRTUAL NET APPLIANCE
- *
- */
- //boolean sendSshKeysToHost(Long hostId, String pubKey, String prvKey):
+ int DEFAULT_ROUTER_VM_RAMSIZE = 256; // 256M
+ int DEFAULT_ROUTER_CPU_MHZ = 500; // 500 MHz
+ boolean USE_POD_VLAN = false;
+ int DEFAULT_PRIORITY = 100;
+ int DEFAULT_DELTA = 2;
+
boolean startRemoteAccessVpn(Network network, RemoteAccessVpn vpn, List<? extends VirtualRouter> routers) throws ResourceUnavailableException;
diff --git a/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java b/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java
index d49322b..ebce049 100644
--- a/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java
+++ b/server/src/main/java/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java
@@ -57,7 +57,6 @@
import org.apache.cloudstack.config.ApiServiceConfiguration;
import org.apache.cloudstack.context.CallContext;
import org.apache.cloudstack.engine.orchestration.service.NetworkOrchestrationService;
-import org.apache.cloudstack.framework.config.ConfigDepot;
import org.apache.cloudstack.framework.config.ConfigKey;
import org.apache.cloudstack.framework.config.Configurable;
import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
@@ -66,7 +65,6 @@
import org.apache.cloudstack.lb.ApplicationLoadBalancerRuleVO;
import org.apache.cloudstack.lb.dao.ApplicationLoadBalancerRuleDao;
import org.apache.cloudstack.managed.context.ManagedContextRunnable;
-import org.apache.cloudstack.network.router.deployment.RouterDeploymentDefinitionBuilder;
import org.apache.cloudstack.network.topology.NetworkTopology;
import org.apache.cloudstack.network.topology.NetworkTopologyContext;
import org.apache.cloudstack.utils.CloudStackVersion;
@@ -116,13 +114,11 @@
import com.cloud.cluster.ManagementServerHostVO;
import com.cloud.cluster.dao.ManagementServerHostDao;
import com.cloud.configuration.Config;
-import com.cloud.configuration.ConfigurationManager;
import com.cloud.configuration.ZoneConfig;
import com.cloud.dc.DataCenter;
import com.cloud.dc.DataCenter.NetworkType;
import com.cloud.dc.DataCenterVO;
import com.cloud.dc.HostPodVO;
-import com.cloud.dc.dao.ClusterDao;
import com.cloud.dc.dao.DataCenterDao;
import com.cloud.dc.dao.HostPodDao;
import com.cloud.dc.dao.VlanDao;
@@ -144,7 +140,6 @@
import com.cloud.host.dao.HostDao;
import com.cloud.hypervisor.Hypervisor.HypervisorType;
import com.cloud.network.IpAddress;
-import com.cloud.network.IpAddressManager;
import com.cloud.network.MonitoringService;
import com.cloud.network.Network;
import com.cloud.network.Network.GuestType;
@@ -178,17 +173,13 @@
import com.cloud.network.dao.NetworkVO;
import com.cloud.network.dao.OpRouterMonitorServiceDao;
import com.cloud.network.dao.OpRouterMonitorServiceVO;
-import com.cloud.network.dao.PhysicalNetworkServiceProviderDao;
import com.cloud.network.dao.RemoteAccessVpnDao;
import com.cloud.network.dao.RouterHealthCheckResultDao;
import com.cloud.network.dao.RouterHealthCheckResultVO;
import com.cloud.network.dao.Site2SiteCustomerGatewayDao;
import com.cloud.network.dao.Site2SiteVpnConnectionDao;
import com.cloud.network.dao.Site2SiteVpnConnectionVO;
-import com.cloud.network.dao.Site2SiteVpnGatewayDao;
-import com.cloud.network.dao.UserIpv6AddressDao;
import com.cloud.network.dao.VirtualRouterProviderDao;
-import com.cloud.network.dao.VpnUserDao;
import com.cloud.network.lb.LoadBalancingRule;
import com.cloud.network.lb.LoadBalancingRule.LbDestination;
import com.cloud.network.lb.LoadBalancingRule.LbHealthCheckPolicy;
@@ -217,16 +208,11 @@
import com.cloud.offering.ServiceOffering;
import com.cloud.offerings.NetworkOfferingVO;
import com.cloud.offerings.dao.NetworkOfferingDao;
-import com.cloud.resource.ResourceManager;
import com.cloud.serializer.GsonHelper;
-import com.cloud.server.ConfigurationServer;
import com.cloud.server.ManagementServer;
import com.cloud.service.ServiceOfferingVO;
import com.cloud.service.dao.ServiceOfferingDao;
import com.cloud.storage.Storage.ProvisioningType;
-import com.cloud.storage.dao.GuestOSDao;
-import com.cloud.storage.dao.VMTemplateDao;
-import com.cloud.storage.dao.VolumeDao;
import com.cloud.user.Account;
import com.cloud.user.AccountManager;
import com.cloud.user.User;
@@ -273,9 +259,7 @@
import com.cloud.vm.dao.NicDao;
import com.cloud.vm.dao.NicIpAliasDao;
import com.cloud.vm.dao.NicIpAliasVO;
-import com.cloud.vm.dao.UserVmDao;
import com.cloud.vm.dao.UserVmDetailsDao;
-import com.cloud.vm.dao.VMInstanceDao;
import com.google.gson.JsonSyntaxException;
import com.google.gson.reflect.TypeToken;
@@ -302,7 +286,6 @@
@Inject private LoadBalancerDao _loadBalancerDao;
@Inject private LoadBalancerVMMapDao _loadBalancerVMMapDao;
@Inject protected IPAddressDao _ipAddressDao;
- @Inject private VMTemplateDao _templateDao;
@Inject protected DomainRouterDao _routerDao;
@Inject private UserDao _userDao;
@Inject protected UserStatisticsDao _userStatsDao;
@@ -313,17 +296,11 @@
@Inject protected AgentManager _agentMgr;
@Inject private AlertManager _alertMgr;
@Inject private AccountManager _accountMgr;
- @Inject private ConfigurationManager _configMgr;
- @Inject private ConfigurationServer _configServer;
@Inject protected ServiceOfferingDao _serviceOfferingDao;
- @Inject private UserVmDao _userVmDao;
- @Inject private VMInstanceDao _vmDao;
@Inject private NetworkOfferingDao _networkOfferingDao;
- @Inject private GuestOSDao _guestOSDao;
@Inject protected NetworkOrchestrationService _networkMgr;
@Inject protected NetworkModel _networkModel;
@Inject protected VirtualMachineManager _itMgr;
- @Inject private VpnUserDao _vpnUsersDao;
@Inject private RulesManager _rulesMgr;
@Inject protected NetworkDao _networkDao;
@Inject private LoadBalancingRulesManager _lbMgr;
@@ -331,21 +308,13 @@
@Inject protected RemoteAccessVpnDao _vpnDao;
@Inject protected NicDao _nicDao;
@Inject private NicIpAliasDao _nicIpAliasDao;
- @Inject private VolumeDao _volumeDao;
@Inject private UserVmDetailsDao _vmDetailsDao;
- @Inject private ClusterDao _clusterDao;
- @Inject private ResourceManager _resourceMgr;
- @Inject private PhysicalNetworkServiceProviderDao _physicalProviderDao;
@Inject protected VirtualRouterProviderDao _vrProviderDao;
@Inject private ManagementServerHostDao _msHostDao;
@Inject private Site2SiteCustomerGatewayDao _s2sCustomerGatewayDao;
- @Inject private Site2SiteVpnGatewayDao _s2sVpnGatewayDao;
@Inject private Site2SiteVpnConnectionDao _s2sVpnConnectionDao;
@Inject private Site2SiteVpnManager _s2sVpnMgr;
- @Inject private UserIpv6AddressDao _ipv6Dao;
@Inject private NetworkService _networkSvc;
- @Inject private IpAddressManager _ipAddrMgr;
- @Inject private ConfigDepot _configDepot;
@Inject protected MonitoringServiceDao _monitorServiceDao;
@Inject private AsyncJobManager _asyncMgr;
@Inject protected VpcDao _vpcDao;
@@ -372,7 +341,6 @@
@Inject protected RouterControlHelper _routerControlHelper;
@Inject protected CommandSetupHelper _commandSetupHelper;
- @Inject protected RouterDeploymentDefinitionBuilder _routerDeploymentManagerBuilder;
@Inject private ManagementServer mgr;
private int _routerRamSize;
@@ -2798,28 +2766,43 @@
final VirtualMachine vm = profile.getVirtualMachine();
final DomainRouterVO domR = _routerDao.findById(vm.getId());
processStopOrRebootAnswer(domR, answer);
- final List<? extends Nic> routerNics = _nicDao.listByVmId(profile.getId());
- for (final Nic nic : routerNics) {
- final Network network = _networkModel.getNetwork(nic.getNetworkId());
- final DataCenterVO dcVO = _dcDao.findById(network.getDataCenterId());
-
- if (network.getTrafficType() == TrafficType.Guest && nic.getBroadcastUri() != null && nic.getBroadcastUri().getScheme().equals("pvlan")) {
- final NicProfile nicProfile = new NicProfile(nic, network, nic.getBroadcastUri(), nic.getIsolationUri(), 0, false, "pvlan-nic");
-
- final NetworkTopology networkTopology = _networkTopologyContext.retrieveNetworkTopology(dcVO);
- try {
- networkTopology.setupDhcpForPvlan(false, domR, domR.getHostId(), nicProfile);
- } catch (final ResourceUnavailableException e) {
- s_logger.debug("ERROR in finalizeStop: ", e);
- }
- }
+ if (Boolean.TRUE.equals(RemoveControlIpOnStop.valueIn(profile.getVirtualMachine().getDataCenterId()))) {
+ removeNics(vm, domR);
}
-
}
}
@Override
public void finalizeExpunge(final VirtualMachine vm) {
+ if (Boolean.FALSE.equals(RemoveControlIpOnStop.valueIn(vm.getDataCenterId()))) {
+ final DomainRouterVO domR = _routerDao.findById(vm.getId());
+ s_logger.info(String.format("removing nics for VR [%s]", vm));
+ removeNics(vm, domR);
+ }
+ }
+
+ private void removeNics(VirtualMachine vm, DomainRouterVO domR) {
+ final List<? extends Nic> routerNics = _nicDao.listByVmId(vm.getId());
+ final DataCenterVO dcVO = _dcDao.findById(vm.getDataCenterId());
+
+ for (final Nic nic : routerNics) {
+ final Network network = _networkModel.getNetwork(nic.getNetworkId());
+
+ removeDhcpRulesForPvLan(domR, nic, network, dcVO);
+ }
+ }
+
+ private void removeDhcpRulesForPvLan(DomainRouterVO domR, Nic nic, Network network, DataCenterVO dcVO) {
+ if (network.getTrafficType() == TrafficType.Guest && nic.getBroadcastUri() != null && nic.getBroadcastUri().getScheme().equals("pvlan")) {
+ final NicProfile nicProfile = new NicProfile(nic, network, nic.getBroadcastUri(), nic.getIsolationUri(), 0, false, "pvlan-nic");
+
+ final NetworkTopology networkTopology = _networkTopologyContext.retrieveNetworkTopology(dcVO);
+ try {
+ networkTopology.setupDhcpForPvlan(false, domR, domR.getHostId(), nicProfile);
+ } catch (final ResourceUnavailableException e) {
+ s_logger.debug("ERROR in finalizeStop: ", e);
+ }
+ }
}
@Override
@@ -3341,7 +3324,8 @@
RouterHealthChecksMaxCpuUsageThreshold,
RouterHealthChecksMaxMemoryUsageThreshold,
ExposeDnsAndBootpServer,
- RouterLogrotateFrequency
+ RouterLogrotateFrequency,
+ RemoveControlIpOnStop
};
}