CLOUDSTACK-8800 : Improved the listVirtualMachines API call to include memory utilization information for a VM for xenserver,kvm and for vmware.

This commit is contained in:
Maneesha.P 2015-10-09 15:46:56 +05:30
parent e5f0788ed1
commit 732a85295d
10 changed files with 148 additions and 13 deletions

View File

@ -32,4 +32,10 @@ public interface VmStats {
public double getDiskWriteKBs();
public double getMemoryKBs();
public double getIntFreeMemoryKBs();
public double getTargetMemoryKBs();
}

View File

@ -196,6 +196,18 @@ public class UserVmResponse extends BaseResponse implements ControlledEntityResp
@Param(description = "the write (bytes) of disk on the vm")
private Long diskKbsWrite;
@SerializedName("memorykbs")
@Param(description = "the memory used by the vm")
private Long memoryKBs;
@SerializedName("memoryintfreekbs")
@Param(description = "the internal memory thats free in vm")
private Long memoryIntFreeKBs;
@SerializedName("memorytargetkbs")
@Param(description = "the target memory in vm")
private Long memoryTargetKBs;
@SerializedName("diskioread")
@Param(description = "the read (io) of disk on the vm")
private Long diskIORead;
@ -466,6 +478,18 @@ public class UserVmResponse extends BaseResponse implements ControlledEntityResp
return diskKbsWrite;
}
public Long getMemoryKBs() {
return memoryKBs;
}
public Long getMemoryIntFreeKBs() {
return memoryIntFreeKBs;
}
public Long getMemoryTargetKBs() {
return memoryTargetKBs;
}
public Long getDiskIORead() {
return diskIORead;
}
@ -645,6 +669,18 @@ public class UserVmResponse extends BaseResponse implements ControlledEntityResp
this.diskIORead = diskIORead;
}
public void setMemoryKBs(Long memoryKBs) {
this.memoryKBs = memoryKBs;
}
public void setMemoryIntFreeKBs(Long memoryIntFreeKBs) {
this.memoryIntFreeKBs = memoryIntFreeKBs;
}
public void setMemoryTargetKBs(Long memoryTargetKBs) {
this.memoryTargetKBs = memoryTargetKBs;
}
public void setDiskIOWrite(Long diskIOWrite) {
this.diskIOWrite = diskIOWrite;
}

View File

@ -30,13 +30,19 @@ public class VmStatsEntry implements VmStats {
double diskWriteIOs;
double diskReadKBs;
double diskWriteKBs;
double memoryKBs;
double intfreememoryKBs;
double targetmemoryKBs;
int numCPUs;
String entityType;
public VmStatsEntry() {
}
public VmStatsEntry(double cpuUtilization, double networkReadKBs, double networkWriteKBs, int numCPUs, String entityType) {
public VmStatsEntry(double memoryKBs,double intfreememoryKBs,double targetmemoryKBs, double cpuUtilization, double networkReadKBs, double networkWriteKBs, int numCPUs, String entityType) {
this.memoryKBs = memoryKBs;
this.intfreememoryKBs = intfreememoryKBs;
this.targetmemoryKBs = targetmemoryKBs;
this.cpuUtilization = cpuUtilization;
this.networkReadKBs = networkReadKBs;
this.networkWriteKBs = networkWriteKBs;
@ -117,6 +123,33 @@ public class VmStatsEntry implements VmStats {
this.diskWriteKBs = diskWriteKBs;
}
@Override
public double getMemoryKBs() {
return memoryKBs;
}
public void setMemoryKBs(double memoryKBs) {
this.memoryKBs = memoryKBs;
}
@Override
public double getIntFreeMemoryKBs() {
return intfreememoryKBs;
}
public void setIntFreeMemoryKBs(double intfreememoryKBs) {
this.intfreememoryKBs = intfreememoryKBs;
}
@Override
public double getTargetMemoryKBs() {
return targetmemoryKBs;
}
public void setTargetMemoryKBs(double targetmemoryKBs) {
this.targetmemoryKBs = targetmemoryKBs;
}
public int getNumCPUs() {
return numCPUs;
}

View File

@ -57,6 +57,7 @@ import org.libvirt.Connect;
import org.libvirt.Domain;
import org.libvirt.DomainBlockStats;
import org.libvirt.DomainInfo;
import org.libvirt.MemoryStatistic;
import org.libvirt.DomainInfo.DomainState;
import org.libvirt.DomainInterfaceStats;
import org.libvirt.LibvirtException;
@ -190,6 +191,7 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
private long _hvVersion;
private long _kernelVersion;
private int _timeout;
private static final int NUMMEMSTATS =2;
private KVMHAMonitor _monitor;
public static final String SSHKEYSPATH = "/root/.ssh";
@ -3018,6 +3020,9 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
long _ioWrote;
long _bytesRead;
long _bytesWrote;
long _intmemfree;
long _memory;
long _maxmemory;
Calendar _timestamp;
}
@ -3026,11 +3031,16 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
try {
dm = getDomain(conn, vmName);
final DomainInfo info = dm.getInfo();
final MemoryStatistic[] mems = dm.memoryStats(NUMMEMSTATS); //number of memory statistics required.
final VmStatsEntry stats = new VmStatsEntry();
stats.setNumCPUs(info.nrVirtCpu);
stats.setEntityType("vm");
stats.setMemoryKBs(info.maxMem);
stats.setTargetMemoryKBs(info.memory);
stats.setIntFreeMemoryKBs((double) mems[0].getValue());
/* get cpu utilization */
VmStats oldStats = null;
@ -3115,6 +3125,9 @@ public class LibvirtComputingResource extends ServerResourceBase implements Serv
newStat._bytesRead = bytes_rd;
newStat._bytesWrote = bytes_wr;
newStat._timestamp = now;
newStat._intmemfree = mems[0].getValue();
newStat._memory = info.memory;
newStat._maxmemory = info.maxMem;
_vmStats.put(vmName, newStat);
return stats;
} finally {

View File

@ -66,6 +66,8 @@ import org.libvirt.DomainInterfaceStats;
import org.libvirt.LibvirtException;
import org.libvirt.NodeInfo;
import org.libvirt.StorageVol;
import org.libvirt.MemoryStatistic;
import org.mockito.Matchers;
import org.mockito.Mock;
import org.mockito.Mockito;
@ -417,7 +419,10 @@ public class LibvirtComputingResourceTest {
final Connect connect = Mockito.mock(Connect.class);
final Domain domain = Mockito.mock(Domain.class);
final DomainInfo domainInfo = new DomainInfo();
final MemoryStatistic[] domainMem = new MemoryStatistic[2];
domainMem[0] = Mockito.mock(MemoryStatistic.class);
Mockito.when(domain.getInfo()).thenReturn(domainInfo);
Mockito.when(domain.memoryStats(2)).thenReturn(domainMem);
Mockito.when(connect.domainLookupByName(VMNAME)).thenReturn(domain);
final NodeInfo nodeInfo = new NodeInfo();
nodeInfo.cpus = 8;
@ -484,6 +489,10 @@ public class LibvirtComputingResourceTest {
// IO traffic as generated by the logic above, must be greater than zero
Assert.assertTrue(vmStat.getDiskReadKBs() > 0);
Assert.assertTrue(vmStat.getDiskWriteKBs() > 0);
// Memory limit of VM must be greater than zero
Assert.assertTrue(vmStat.getIntFreeMemoryKBs() >= 0);
Assert.assertTrue(vmStat.getMemoryKBs() >= 0);
Assert.assertTrue(vmStat.getTargetMemoryKBs() >= vmStat.getMemoryKBs());
}
@Test
@ -5021,4 +5030,4 @@ public class LibvirtComputingResourceTest {
}
}
}
}
}

View File

@ -319,7 +319,7 @@ public class MockVmManagerImpl extends ManagerBase implements MockVmManager {
final HashMap<String, VmStatsEntry> vmStatsNameMap = new HashMap<String, VmStatsEntry>();
final List<String> vmNames = cmd.getVmNames();
for (final String vmName : vmNames) {
final VmStatsEntry entry = new VmStatsEntry(0, 0, 0, 0, "vm");
final VmStatsEntry entry = new VmStatsEntry(0, 0, 0, 0, 0, 0, 0, "vm");
entry.setNetworkReadKBs(32768); // default values 256 KBps
entry.setNetworkWriteKBs(16384);
entry.setCPUUtilization(10);

View File

@ -99,6 +99,7 @@ import com.vmware.vim25.VmwareDistributedVirtualSwitchVlanIdSpec;
import org.apache.cloudstack.storage.command.StorageSubSystemCommand;
import org.apache.cloudstack.storage.to.TemplateObjectTO;
import org.apache.cloudstack.storage.to.VolumeObjectTO;
import org.apache.commons.lang.math.NumberUtils;
import com.cloud.agent.IAgentControl;
import com.cloud.agent.api.Answer;
@ -4862,8 +4863,14 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
}
String instanceNameCustomField = "value[" + key + "]";
final String numCpuStr = "summary.config.numCpu";
final String cpuUseStr = "summary.quickStats.overallCpuUsage";
final String guestMemUseStr = "summary.quickStats.guestMemoryUsage";
final String memLimitStr = "resourceConfig.memoryAllocation.limit";
final String memMbStr = "config.hardware.memoryMB";
ObjectContent[] ocs =
hyperHost.getVmPropertiesOnHyperHost(new String[] {"name", "summary.config.numCpu", "summary.quickStats.overallCpuUsage", instanceNameCustomField});
hyperHost.getVmPropertiesOnHyperHost(new String[] {"name", numCpuStr, cpuUseStr ,guestMemUseStr ,memLimitStr ,memMbStr, instanceNameCustomField});
if (ocs != null && ocs.length > 0) {
for (ObjectContent oc : ocs) {
List<DynamicProperty> objProps = oc.getPropSet();
@ -4871,6 +4878,9 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
String name = null;
String numberCPUs = null;
String maxCpuUsage = null;
String memlimit = null;
String memkb = null;
String guestMemusage = null;
String vmNameOnVcenter = null;
String vmInternalCSName = null;
for (DynamicProperty objProp : objProps) {
@ -4879,10 +4889,16 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
} else if (objProp.getName().contains(instanceNameCustomField)) {
if (objProp.getVal() != null)
vmInternalCSName = ((CustomFieldStringValue)objProp.getVal()).getValue();
} else if (objProp.getName().equals("summary.config.numCpu")) {
}else if(objProp.getName().equals(guestMemusage)){
guestMemusage = objProp.getVal().toString();
}else if (objProp.getName().equals(numCpuStr)) {
numberCPUs = objProp.getVal().toString();
} else if (objProp.getName().equals("summary.quickStats.overallCpuUsage")) {
} else if (objProp.getName().equals(cpuUseStr)) {
maxCpuUsage = objProp.getVal().toString();
} else if (objProp.getName().equals(memLimitStr)) {
memlimit = objProp.getVal().toString();
} else if (objProp.getName().equals(memMbStr)) {
memkb = objProp.getVal().toString();
}
}
new VirtualMachineMO(hyperHost.getContext(), oc.getObj());
@ -4951,7 +4967,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
}
}
}
vmResponseMap.put(name, new VmStatsEntry(Integer.parseInt(maxCpuUsage), networkReadKBs, networkWriteKBs, Integer.parseInt(numberCPUs), "vm"));
vmResponseMap.put(name, new VmStatsEntry( NumberUtils.toDouble(memkb)*1024,NumberUtils.toDouble(guestMemusage)*1024,NumberUtils.toDouble(memlimit)*1024, NumberUtils.toDouble(maxCpuUsage), networkReadKBs, networkWriteKBs, NumberUtils.toInt(numberCPUs), "vm"));
}
}
}

View File

@ -3278,7 +3278,7 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
final HashMap<String, VmStatsEntry> vmResponseMap = new HashMap<String, VmStatsEntry>();
for (final String vmUUID : vmUUIDs) {
vmResponseMap.put(vmUUID, new VmStatsEntry(0, 0, 0, 0, "vm"));
vmResponseMap.put(vmUUID, new VmStatsEntry(0,0,0,0, 0, 0, 0, "vm"));
}
final Object[] rrdData = getRRDData(conn, 2); // call rrddata with 2 for
@ -3332,7 +3332,14 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
vmStatsAnswer.setDiskReadKBs(vmStatsAnswer.getDiskReadKBs() + getDataAverage(dataNode, col, numRows) / 1000);
} else if (param.matches("vbd_.*_write")) {
vmStatsAnswer.setDiskWriteKBs(vmStatsAnswer.getDiskWriteKBs() + getDataAverage(dataNode, col, numRows) / 1000);
} else if (param.contains("memory_internal_free")) {
vmStatsAnswer.setIntFreeMemoryKBs(vmStatsAnswer.getIntFreeMemoryKBs() + getDataAverage(dataNode, col, numRows) / 1024);
} else if (param.contains("memory_target")) {
vmStatsAnswer.setTargetMemoryKBs(vmStatsAnswer.getTargetMemoryKBs() + getDataAverage(dataNode, col, numRows) / 1024);
} else if (param.contains("memory")) {
vmStatsAnswer.setMemoryKBs(vmStatsAnswer.getMemoryKBs() + getDataAverage(dataNode, col, numRows) / 1024);
}
}
}
@ -3348,6 +3355,7 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
s_logger.debug("Vm cpu utilization " + vmStatsAnswer.getCPUUtilization());
}
}
return vmResponseMap;
}
@ -5394,4 +5402,4 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
}
}
}

View File

@ -207,14 +207,21 @@ public class UserVmJoinDaoImpl extends GenericDaoBase<UserVmJoinVO, Long> implem
userVmResponse.setNetworkKbsWrite((long)vmStats.getNetworkWriteKBs());
if ((userVm.getHypervisorType() != null) && (userVm.getHypervisorType().equals(HypervisorType.KVM) || userVm.getHypervisorType().equals(HypervisorType.XenServer))) { // support KVM and XenServer only util 2013.06.25
if ((userVm.getHypervisorType() != null) && (userVm.getHypervisorType().equals(HypervisorType.KVM) || userVm.getHypervisorType().equals(HypervisorType.XenServer) || userVm.getHypervisorType().equals(HypervisorType.VMware))) { // support KVM and XenServer only util 2013.06.25 . supporting Vmware from 2015.09.02
userVmResponse.setDiskKbsRead((long)vmStats.getDiskReadKBs());
userVmResponse.setDiskKbsWrite((long)vmStats.getDiskWriteKBs());
userVmResponse.setDiskKbsWrite((long) vmStats.getDiskWriteKBs());
userVmResponse.setDiskIORead((long)vmStats.getDiskReadIOs());
userVmResponse.setDiskIORead((long) vmStats.getDiskReadIOs());
userVmResponse.setDiskIOWrite((long) vmStats.getDiskWriteIOs());
userVmResponse.setMemoryKBs((long) vmStats.getMemoryKBs());
userVmResponse.setMemoryIntFreeKBs((long) vmStats.getIntFreeMemoryKBs());
userVmResponse.setMemoryTargetKBs((long) vmStats.getTargetMemoryKBs());
userVmResponse.setDiskIOWrite((long)vmStats.getDiskWriteIOs());
}
}
}

View File

@ -462,6 +462,9 @@ public class StatsCollector extends ManagerBase implements ComponentMethodInterc
statsInMemory.setDiskReadIOs(statsInMemory.getDiskReadIOs() + statsForCurrentIteration.getDiskReadIOs());
statsInMemory.setDiskWriteIOs(statsInMemory.getDiskWriteIOs() + statsForCurrentIteration.getDiskWriteIOs());
statsInMemory.setDiskReadKBs(statsInMemory.getDiskReadKBs() + statsForCurrentIteration.getDiskReadKBs());
statsInMemory.setMemoryKBs(statsForCurrentIteration.getMemoryKBs());
statsInMemory.setIntFreeMemoryKBs(statsForCurrentIteration.getIntFreeMemoryKBs());
statsInMemory.setTargetMemoryKBs(statsForCurrentIteration.getTargetMemoryKBs());
_VmStats.put(vmId, statsInMemory);
}
@ -482,6 +485,10 @@ public class StatsCollector extends ManagerBase implements ComponentMethodInterc
metrics.put(externalStatsPrefix + "cloudstack.stats.instances." + vmName + ".disk.read_kbs", statsForCurrentIteration.getDiskReadKBs());
metrics.put(externalStatsPrefix + "cloudstack.stats.instances." + vmName + ".disk.write_iops", statsForCurrentIteration.getDiskWriteIOs());
metrics.put(externalStatsPrefix + "cloudstack.stats.instances." + vmName + ".disk.read_iops", statsForCurrentIteration.getDiskReadIOs());
metrics.put(externalStatsPrefix + "cloudstack.stats.instances." + vmName + ".memory.total_kbs", statsForCurrentIteration.getMemoryKBs());
metrics.put(externalStatsPrefix + "cloudstack.stats.instances." + vmName + ".memory.internalfree_kbs", statsForCurrentIteration.getIntFreeMemoryKBs());
metrics.put(externalStatsPrefix + "cloudstack.stats.instances." + vmName + ".memory.target_kbs", statsForCurrentIteration.getTargetMemoryKBs());
}
}