diff --git a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java index 02607e94fc8..883c8c99429 100755 --- a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java +++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java @@ -2201,6 +2201,17 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv } private void createVif(final LibvirtVMDef vm, final NicTO nic, final String nicAdapter) throws InternalErrorException, LibvirtException { + + if (nic.getType().equals(TrafficType.Guest) && nic.getBroadcastType().equals(BroadcastDomainType.Vsp)) { + String vrIp = nic.getBroadcastUri().getPath().substring(1); + vm.getMetaData().getMetadataNode(LibvirtVMDef.NuageExtensionDef.class).addNuageExtension(nic.getMac(), vrIp); + + if (s_logger.isDebugEnabled()) { + s_logger.debug("NIC with MAC " + nic.getMac() + " and BroadcastDomainType " + nic.getBroadcastType() + " in network(" + nic.getGateway() + "/" + nic.getNetmask() + + ") is " + nic.getType() + " traffic type. So, vsp-vr-ip " + vrIp + " is set in the metadata"); + } + } + vm.getDevices().addDevice(getVifDriver(nic.getType()).plug(nic, vm.getPlatformEmulator().toString(), nicAdapter).toString()); } diff --git a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtVMDef.java b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtVMDef.java index 7310f1253bb..6ce7d6c8f5e 100644 --- a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtVMDef.java +++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtVMDef.java @@ -16,7 +16,9 @@ // under the License. package com.cloud.hypervisor.kvm.resource; +import com.google.common.collect.Maps; import org.apache.commons.lang.StringEscapeUtils; +import org.apache.log4j.Logger; import java.util.ArrayList; import java.util.HashMap; @@ -24,6 +26,8 @@ import java.util.List; import java.util.Map; public class LibvirtVMDef { + private static final Logger s_logger = Logger.getLogger(LibvirtVMDef.class); + private String _hvsType; private static long s_libvirtVersion; private static long s_qemuVersion; @@ -1311,6 +1315,57 @@ public class LibvirtVMDef { } } + public static class MetadataDef { + Map customNodes = new HashMap<>(); + + public T getMetadataNode(Class fieldClass) { + T field = (T) customNodes.get(fieldClass.getName()); + if (field == null) { + try { + field = fieldClass.newInstance(); + customNodes.put(field.getClass().getName(), field); + } catch (InstantiationException | IllegalAccessException e) { + s_logger.debug("No default constructor available in class " + fieldClass.getName() + ", ignoring exception", e); + } + } + return field; + } + + @Override + public String toString() { + StringBuilder fsBuilder = new StringBuilder(); + fsBuilder.append("\n"); + for (Object field : customNodes.values()) { + fsBuilder.append(field.toString()); + } + fsBuilder.append("\n"); + return fsBuilder.toString(); + } + } + + public static class NuageExtensionDef { + private Map addresses = Maps.newHashMap(); + + public void addNuageExtension(String macAddress, String vrIp) { + addresses.put(macAddress, vrIp); + } + + @Override + public String toString() { + StringBuilder fsBuilder = new StringBuilder(); + for (Map.Entry address : addresses.entrySet()) { + fsBuilder.append("\n") + .append(" \n") + .append("\n"); + } + return fsBuilder.toString(); + } + } + public void setHvsType(String hvs) { _hvsType = hvs; } @@ -1371,6 +1426,15 @@ public class LibvirtVMDef { return null; } + public MetadataDef getMetaData() { + MetadataDef o = (MetadataDef) components.get(MetadataDef.class.toString()); + if (o == null) { + o = new MetadataDef(); + addComp(o); + } + return o; + } + @Override public String toString() { StringBuilder vmBuilder = new StringBuilder(); diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java index 5cb7fda3693..c5f7ceec3ec 100644 --- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java +++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java @@ -937,8 +937,8 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa NicTO nicTo = cmd.getNic(); VirtualDevice nic; Pair networkInfo = prepareNetworkFromNicInfo(vmMo.getRunningHost(), nicTo, false, cmd.getVMType()); + String dvSwitchUuid = null; if (VmwareHelper.isDvPortGroup(networkInfo.first())) { - String dvSwitchUuid; ManagedObjectReference dcMor = hyperHost.getHyperHostDatacenter(); DatacenterMO dataCenterMo = new DatacenterMO(context, dcMor); ManagedObjectReference dvsMor = dataCenterMo.getDvSwitchMor(networkInfo.first()); @@ -961,7 +961,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa deviceConfigSpec.setOperation(VirtualDeviceConfigSpecOperation.ADD); vmConfigSpec.getDeviceChange().add(deviceConfigSpec); - setNuageVspVrIpInExtraConfig(vmConfigSpec.getExtraConfig(), nicTo); + setNuageVspVrIpInExtraConfig(vmConfigSpec.getExtraConfig(), nicTo, dvSwitchUuid); if (!vmMo.configureVm(vmConfigSpec)) { throw new Exception("Failed to configure devices when running PlugNicCommand"); } @@ -1681,6 +1681,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa NiciraNvpApiVersion.logNiciraApiVersion(); + Map nicUuidToDvSwitchUuid = new HashMap(); for (NicTO nicTo : sortNicsByDeviceId(nics)) { s_logger.info("Prepare NIC device based on NicTO: " + _gson.toJson(nicTo)); @@ -1699,6 +1700,9 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa nic = VmwareHelper.prepareDvNicDevice(vmMo, networkInfo.first(), nicDeviceType, networkInfo.second(), dvSwitchUuid, nicTo.getMac(), nicUnitNumber++, i + 1, true, true); + if (nicTo.getUuid() != null) { + nicUuidToDvSwitchUuid.put(nicTo.getUuid(), dvSwitchUuid); + } } else { s_logger.info("Preparing NIC device on network " + networkInfo.second()); nic = @@ -1735,7 +1739,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa // pass boot arguments through machine.id & perform customized options to VMX ArrayList extraOptions = new ArrayList(); configBasicExtraOption(extraOptions, vmSpec); - configNvpExtraOption(extraOptions, vmSpec); + configNvpExtraOption(extraOptions, vmSpec, nicUuidToDvSwitchUuid); configCustomExtraOption(extraOptions, vmSpec); // config VNC @@ -1945,7 +1949,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa extraOptions.add(newVal); } - private static void configNvpExtraOption(List extraOptions, VirtualMachineTO vmSpec) { + private static void configNvpExtraOption(List extraOptions, VirtualMachineTO vmSpec, Map nicUuidToDvSwitchUuid) { /** * Extra Config : nvp.vm-uuid = uuid * - Required for Nicira NVP integration @@ -1966,20 +1970,33 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa newVal.setKey("nvp.iface-id." + nicNum); newVal.setValue(nicTo.getUuid()); extraOptions.add(newVal); - setNuageVspVrIpInExtraConfig(extraOptions, nicTo); + setNuageVspVrIpInExtraConfig(extraOptions, nicTo, nicUuidToDvSwitchUuid.get(nicTo.getUuid())); } nicNum++; } } - private static void setNuageVspVrIpInExtraConfig(List extraOptions, NicTO nicTo) { - URI broadcastUri = nicTo.getBroadcastUri(); - if (broadcastUri != null && broadcastUri.getScheme().equalsIgnoreCase(Networks.BroadcastDomainType.Vsp.scheme())) { - String path = broadcastUri.getPath(); - OptionValue newVal = new OptionValue(); + private static void setNuageVspVrIpInExtraConfig(List extraOptions, NicTO nicTo, String dvSwitchUuid) { + if (nicTo.getBroadcastType() != BroadcastDomainType.Vsp) { + return; + } + + OptionValue newVal; + if (nicTo.getType().equals(TrafficType.Guest) && dvSwitchUuid != null && nicTo.getGateway() != null && nicTo.getNetmask() != null) { + String vrIp = nicTo.getBroadcastUri().getPath().substring(1); + newVal = new OptionValue(); newVal.setKey("vsp.vr-ip." + nicTo.getMac()); - newVal.setValue(path.substring(1)); + newVal.setValue(vrIp); extraOptions.add(newVal); + newVal = new OptionValue(); + newVal.setKey("vsp.dvswitch." + nicTo.getMac()); + newVal.setValue(dvSwitchUuid); + extraOptions.add(newVal); + + if (s_logger.isDebugEnabled()) { + s_logger.debug("NIC with MAC " + nicTo.getMac() + " and BroadcastDomainType " + nicTo.getBroadcastType() + " in network(" + nicTo.getGateway() + "/" + + nicTo.getNetmask() + ") is " + nicTo.getType() + " traffic type. So, vsp-vr-ip is set in the extraconfig"); + } } }