From: Hyman Huang(黄勇) <huangy81(a)chinatelecom.cn>
Extend qemuDomainGetVcpus for getting dirtylimit info so that
'virsh vcpuinfo' api can display vcpu dirty page rate limit.
Signed-off-by: Hyman Huang(黄勇) <huangy81(a)chinatelecom.cn>
---
include/libvirt/libvirt-domain.h | 2 ++
src/qemu/qemu_driver.c | 62 ++++++++++++++++++++++++++++++++++++++++
2 files changed, 64 insertions(+)
diff --git a/include/libvirt/libvirt-domain.h b/include/libvirt/libvirt-domain.h
index 2e49224..24348d0 100644
--- a/include/libvirt/libvirt-domain.h
+++ b/include/libvirt/libvirt-domain.h
@@ -2365,6 +2365,8 @@ struct _virVcpuInfo {
int state; /* value from virVcpuState */
unsigned long long cpuTime; /* CPU time used, in nanoseconds */
int cpu; /* real CPU number, or one of the values from
virVcpuHostCpuState */
+ unsigned long long limit; /* virtual cpu dirty page rate limit in MB/s */
+ unsigned long long current; /* virtual cpu dirty page rate in MB/s */
};
/**
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 981027a..235a187 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -4756,6 +4756,64 @@ qemuDomainGetEmulatorPinInfo(virDomainPtr dom,
}
static int
+qemuDomainGetVcpuDirtyLimit(virDomainPtr dom,
+ virDomainObj *vm,
+ virVcpuInfoPtr info,
+ int maxinfo)
+{
+ qemuDomainObjPrivate *priv = vm->privateData;
+ qemuMonitorVcpuDirtyLimitInfo dirtylimit_info;
+ size_t ncpuinfo = 0;
+ size_t i;
+ int ret = -1;
+
+ if (!virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_VCPU_DIRTY_LIMIT))
+ return 0;
+
+ if (qemuDomainObjBeginJob(vm, VIR_JOB_MODIFY) < 0)
+ goto endjob;
+
+ if (virDomainObjCheckActive(vm) < 0)
+ goto endjob;
+
+ qemuDomainObjEnterMonitor(vm);
+ if (qemuMonitorQueryVcpuDirtyLimit(priv->mon, &dirtylimit_info) < 0) {
+ qemuDomainObjExitMonitor(vm);
+ goto endjob;
+ }
+ qemuDomainObjExitMonitor(vm);
+
+ /* qemu allow to set dirty page limit for hotpluggable vcpu, which
+ * therefore may return unhotpluggable vcpu dirty limit info for
+ * qmp command 'query-vcpu-dirty-limit', filter out that */
+ for (i = 0; i < dirtylimit_info.nvcpus && ncpuinfo < maxinfo; i++) {
+ int cpu_index = dirtylimit_info.limits[i].idx;
+
+ /* cpu index greater than array size of cpu info, which means
+ * the remaining cpus are hotpluggable but not active */
+ if (cpu_index >= maxinfo)
+ break;
+
+ virDomainVcpuDef *vcpu = virDomainDefGetVcpu(vm->def, cpu_index);
+
+ if (!vcpu->online)
+ continue;
+
+ virVcpuInfoPtr vcpuinfo = info + cpu_index;
+
+ vcpuinfo->current = dirtylimit_info.limits[i].current;
+ vcpuinfo->limit = dirtylimit_info.limits[i].limit;
+
+ ncpuinfo++;
+ }
+ ret = 0;
+
+ endjob:
+ qemuDomainObjEndJob(vm);
+ return ret;
+}
+
+static int
qemuDomainGetVcpus(virDomainPtr dom,
virVcpuInfoPtr info,
int maxinfo,
@@ -4779,6 +4837,10 @@ qemuDomainGetVcpus(virDomainPtr dom,
ret = qemuDomainHelperGetVcpus(vm, info, NULL, NULL, maxinfo, cpumaps, maplen);
+ /* append dirty limit data to vcpu info */
+ if (qemuDomainGetVcpuDirtyLimit(dom, vm, info, maxinfo) < 0)
+ goto cleanup;
+
cleanup:
virDomainObjEndAPI(&vm);
return ret;
--
1.8.3.1