Bug-Id: CLOUDSTACK-3439: Include dynamically created nics in Prepare for migration command in KVM
Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/f767adfe Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/f767adfe Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/f767adfe Branch: refs/heads/vmware-disk-controllers Commit: f767adfe71dda82c45cf376ba71518e2ad84cc98 Parents: a520309 Author: Kishan Kavala <kis...@apache.org> Authored: Wed Jan 7 14:52:42 2015 +0530 Committer: Kishan Kavala <kis...@apache.org> Committed: Wed Jan 7 14:52:42 2015 +0530 ---------------------------------------------------------------------- api/src/com/cloud/vm/NicProfile.java | 8 ++ .../service/NetworkOrchestrationService.java | 2 + .../com/cloud/vm/VirtualMachineManagerImpl.java | 1 + .../orchestration/NetworkOrchestrator.java | 86 ++++++++++++++++++++ .../src/com/cloud/network/dao/IPAddressDao.java | 1 + .../com/cloud/network/dao/IPAddressDaoImpl.java | 7 ++ .../cloud/hypervisor/HypervisorGuruBase.java | 4 + .../com/cloud/vpc/MockNetworkManagerImpl.java | 5 ++ 8 files changed, 114 insertions(+) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/api/src/com/cloud/vm/NicProfile.java ---------------------------------------------------------------------- diff --git a/api/src/com/cloud/vm/NicProfile.java b/api/src/com/cloud/vm/NicProfile.java index 4dd7f68..e9e9dc5 100644 --- a/api/src/com/cloud/vm/NicProfile.java +++ b/api/src/com/cloud/vm/NicProfile.java @@ -70,6 +70,10 @@ public class NicProfile implements InternalIdentity, Serializable { return name; } + public void setName(String name) { + this.name = name; + } + public String getDns2() { return dns2; } @@ -371,4 +375,8 @@ public class NicProfile implements InternalIdentity, Serializable { this.ip6Dns2 = ip6Dns2; } + public void setNetworId(long networkId){ + this.networkId = networkId; + } + } http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/engine/api/src/org/apache/cloudstack/engine/orchestration/service/NetworkOrchestrationService.java ---------------------------------------------------------------------- diff --git a/engine/api/src/org/apache/cloudstack/engine/orchestration/service/NetworkOrchestrationService.java b/engine/api/src/org/apache/cloudstack/engine/orchestration/service/NetworkOrchestrationService.java index b2108ac..5412ee4 100644 --- a/engine/api/src/org/apache/cloudstack/engine/orchestration/service/NetworkOrchestrationService.java +++ b/engine/api/src/org/apache/cloudstack/engine/orchestration/service/NetworkOrchestrationService.java @@ -217,4 +217,6 @@ public interface NetworkOrchestrationService { void removeDhcpServiceInSubnet(Nic nic); boolean resourceCountNeedsUpdate(NetworkOffering ntwkOff, ACLType aclType); + + void prepareAllNicsForMigration(VirtualMachineProfile vm, DeployDestination dest); } http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java ---------------------------------------------------------------------- diff --git a/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java b/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java index 8accebe..ca60529 100644 --- a/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java +++ b/engine/orchestration/src/com/cloud/vm/VirtualMachineManagerImpl.java @@ -3284,6 +3284,7 @@ public class VirtualMachineManagerImpl extends ManagerBase implements VirtualMac VirtualMachineProfile profile = new VirtualMachineProfileImpl(vm); _networkMgr.prepareNicForMigration(profile, dest); + volumeMgr.prepareForMigration(profile, dest); VirtualMachineTO to = toVmTO(profile); http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/engine/orchestration/src/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java ---------------------------------------------------------------------- diff --git a/engine/orchestration/src/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java b/engine/orchestration/src/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java index 4e42750..9feaa80 100644 --- a/engine/orchestration/src/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java +++ b/engine/orchestration/src/org/apache/cloudstack/engine/orchestration/NetworkOrchestrator.java @@ -37,6 +37,7 @@ import javax.ejb.Local; import javax.inject.Inject; import javax.naming.ConfigurationException; +import com.cloud.network.Networks; import org.apache.log4j.Logger; import org.apache.cloudstack.acl.ControlledEntity.ACLType; import org.apache.cloudstack.context.CallContext; @@ -1376,6 +1377,11 @@ public class NetworkOrchestrator extends ManagerBase implements NetworkOrchestra @Override public void prepareNicForMigration(VirtualMachineProfile vm, DeployDestination dest) { + if(vm.getType().equals(VirtualMachine.Type.DomainRouter) && vm.getHypervisorType().equals(HypervisorType.KVM)){ + //Include nics hot plugged and not stored in DB + prepareAllNicsForMigration(vm, dest); + return; + } List<NicVO> nics = _nicDao.listByVmId(vm.getId()); ReservationContext context = new ReservationContextImpl(UUID.randomUUID().toString(), null, null); for (NicVO nic : nics) { @@ -1409,6 +1415,86 @@ public class NetworkOrchestrator extends ManagerBase implements NetworkOrchestra } } + /* + Prepare All Nics for migration including the nics dynamically created and not stored in DB + This is a temporary workaround work KVM migration + Once clean fix is added by stored dynamically nics is DB, this workaround won't be needed + */ + @Override + public void prepareAllNicsForMigration(VirtualMachineProfile vm, DeployDestination dest) { + List<NicVO> nics = _nicDao.listByVmId(vm.getId()); + ReservationContext context = new ReservationContextImpl(UUID.randomUUID().toString(), null, null); + Long guestNetworkId = null; + for (NicVO nic : nics) { + NetworkVO network = _networksDao.findById(nic.getNetworkId()); + if(network.getTrafficType().equals(TrafficType.Guest) && network.getGuestType().equals(GuestType.Isolated)){ + guestNetworkId = network.getId(); + } + Integer networkRate = _networkModel.getNetworkRate(network.getId(), vm.getId()); + + NetworkGuru guru = AdapterBase.getAdapterByName(networkGurus, network.getGuruName()); + NicProfile profile = new NicProfile(nic, network, nic.getBroadcastUri(), nic.getIsolationUri(), networkRate, + _networkModel.isSecurityGroupSupportedInNetwork(network), _networkModel.getNetworkTag(vm.getHypervisorType(), network)); + if(guru instanceof NetworkMigrationResponder){ + if(!((NetworkMigrationResponder) guru).prepareMigration(profile, network, vm, dest, context)){ + s_logger.error("NetworkGuru "+guru+" prepareForMigration failed."); // XXX: Transaction error + } + } + List<Provider> providersToImplement = getNetworkProviders(network.getId()); + for (NetworkElement element : networkElements) { + if (providersToImplement.contains(element.getProvider())) { + if (!_networkModel.isProviderEnabledInPhysicalNetwork(_networkModel.getPhysicalNetworkId(network), element.getProvider().getName())) { + throw new CloudRuntimeException("Service provider " + element.getProvider().getName() + " either doesn't exist or is not enabled in physical network id: " + network.getPhysicalNetworkId()); + } + if(element instanceof NetworkMigrationResponder){ + if(!((NetworkMigrationResponder) element).prepareMigration(profile, network, vm, dest, context)){ + s_logger.error("NetworkElement "+element+" prepareForMigration failed."); // XXX: Transaction error + } + } + } + } + guru.updateNicProfile(profile, network); + vm.addNic(profile); + } + + List<String> addedURIs = new ArrayList<String>(); + if(guestNetworkId != null){ + List<IPAddressVO> publicIps = _ipAddressDao.listByAssociatedNetwork(guestNetworkId, null); + for (IPAddressVO userIp : publicIps){ + PublicIp publicIp = PublicIp.createFromAddrAndVlan(userIp, _vlanDao.findById(userIp.getVlanId())); + URI broadcastUri = BroadcastDomainType.Vlan.toUri(publicIp.getVlanTag()); + long ntwkId = publicIp.getNetworkId(); + Nic nic = _nicDao.findByNetworkIdInstanceIdAndBroadcastUri(ntwkId, vm.getId(), + broadcastUri.toString()); + if(nic == null && !addedURIs.contains(broadcastUri.toString())){ + //Nic details are not available in DB + //Create nic profile for migration + s_logger.debug("Creating nic profile for migration. BroadcastUri: "+broadcastUri.toString()+" NetworkId: "+ntwkId+" Vm: "+vm.getId()); + NetworkVO network = _networksDao.findById(ntwkId); + Integer networkRate = _networkModel.getNetworkRate(network.getId(), vm.getId()); + NetworkGuru guru = AdapterBase.getAdapterByName(networkGurus, network.getGuruName()); + NicProfile profile = new NicProfile(); + profile.setDeviceId(255); //dummyId + profile.setIp4Address(userIp.getAddress().toString()); + profile.setNetmask(publicIp.getNetmask()); + profile.setGateway(publicIp.getGateway()); + profile.setMacAddress(publicIp.getMacAddress()); + profile.setBroadcastType(network.getBroadcastDomainType()); + profile.setTrafficType(network.getTrafficType()); + profile.setBroadcastUri(broadcastUri); + profile.setIsolationUri(Networks.IsolationType.Vlan.toUri(publicIp.getVlanTag())); + profile.setSecurityGroupEnabled(_networkModel.isSecurityGroupSupportedInNetwork(network)); + profile.setName(_networkModel.getNetworkTag(vm.getHypervisorType(), network)); + profile.setNetworId(network.getId()); + + guru.updateNicProfile(profile, network); + vm.addNic(profile); + addedURIs.add(broadcastUri.toString()); + } + } + } + } + private NicProfile findNicProfileById(VirtualMachineProfile vm, long id) { for (NicProfile nic : vm.getNics()) { if (nic.getId() == id) { http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/engine/schema/src/com/cloud/network/dao/IPAddressDao.java ---------------------------------------------------------------------- diff --git a/engine/schema/src/com/cloud/network/dao/IPAddressDao.java b/engine/schema/src/com/cloud/network/dao/IPAddressDao.java index 8d60b57..cb07656 100644 --- a/engine/schema/src/com/cloud/network/dao/IPAddressDao.java +++ b/engine/schema/src/com/cloud/network/dao/IPAddressDao.java @@ -84,4 +84,5 @@ public interface IPAddressDao extends GenericDao<IPAddressVO, Long> { void lockRange(long vlandbId); + List<IPAddressVO> listByAssociatedVmId(long vmId); } http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/engine/schema/src/com/cloud/network/dao/IPAddressDaoImpl.java ---------------------------------------------------------------------- diff --git a/engine/schema/src/com/cloud/network/dao/IPAddressDaoImpl.java b/engine/schema/src/com/cloud/network/dao/IPAddressDaoImpl.java index 6f6bfd2..5122876 100644 --- a/engine/schema/src/com/cloud/network/dao/IPAddressDaoImpl.java +++ b/engine/schema/src/com/cloud/network/dao/IPAddressDaoImpl.java @@ -431,6 +431,13 @@ public class IPAddressDaoImpl extends GenericDaoBase<IPAddressVO, Long> implemen } @Override + public List<IPAddressVO> listByAssociatedVmId(long vmId) { + SearchCriteria<IPAddressVO> sc = AllFieldsSearch.create(); + sc.setParameters("associatedWithVmId", vmId); + return listBy(sc); + } + + @Override public void lockRange(long vlandbId) { SearchCriteria<IPAddressVO> sc = AllFieldsSearch.create(); sc.setParameters("vlan", vlandbId); http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/server/src/com/cloud/hypervisor/HypervisorGuruBase.java ---------------------------------------------------------------------- diff --git a/server/src/com/cloud/hypervisor/HypervisorGuruBase.java b/server/src/com/cloud/hypervisor/HypervisorGuruBase.java index 308c327..0cb9af5 100644 --- a/server/src/com/cloud/hypervisor/HypervisorGuruBase.java +++ b/server/src/com/cloud/hypervisor/HypervisorGuruBase.java @@ -18,6 +18,7 @@ package com.cloud.hypervisor; import java.util.List; import java.util.Map; +import java.util.UUID; import javax.inject.Inject; @@ -112,6 +113,9 @@ public abstract class HypervisorGuruBase extends AdapterBase implements Hypervis to.setNicSecIps(secIps); } else { s_logger.warn("Unabled to load NicVO for NicProfile " + profile.getId()); + //Workaround for dynamically created nics + //FixMe: uuid and secondary IPs can be made part of nic profile + to.setUuid(UUID.randomUUID().toString()); } //check whether the this nic has secondary ip addresses set http://git-wip-us.apache.org/repos/asf/cloudstack/blob/f767adfe/server/test/com/cloud/vpc/MockNetworkManagerImpl.java ---------------------------------------------------------------------- diff --git a/server/test/com/cloud/vpc/MockNetworkManagerImpl.java b/server/test/com/cloud/vpc/MockNetworkManagerImpl.java index 097019d..e4c97a0 100644 --- a/server/test/com/cloud/vpc/MockNetworkManagerImpl.java +++ b/server/test/com/cloud/vpc/MockNetworkManagerImpl.java @@ -839,6 +839,11 @@ public class MockNetworkManagerImpl extends ManagerBase implements NetworkOrches } @Override + public void prepareAllNicsForMigration(VirtualMachineProfile vm, DeployDestination dest) { + return; + } + + @Override public void prepareNicForMigration(VirtualMachineProfile vm, DeployDestination dest) { // TODO Auto-generated method stub