]> xenbits.xensource.com Git - qemu-xen-4.5-testing.git/commitdiff
Implement 'xm vcpu-set' command for HVM guest
authorIan Jackson <ian.jackson@eu.citrix.com>
Fri, 30 Apr 2010 16:41:45 +0000 (17:41 +0100)
committerIan Jackson <Ian.Jackson@eu.citrix.com>
Fri, 30 Apr 2010 16:41:45 +0000 (17:41 +0100)
Currently Xen has 'xm vcpu-set' command for PV domain, but not
available for HVM domain.  This patch is use to enable 'xm vcpu-set'
command for HVM domain. It setup vcpu watch at xenstore, and at qemu
side, handle vcpu online/offline accordingly.  With this patch, 'xm
vcpu-set' command works for both PV and HVM guest with same format.

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>
hw/piix4acpi.c
xenstore.c

index 3c52c4bf4b142e7fd633c1dcab9f43ed8dccb3ca..1efa77dae42eac0bb73666cdee5ecd9c883cde7a 100644 (file)
@@ -749,8 +749,8 @@ static int disable_processor(GPEState *g, int cpu)
 
 void qemu_cpu_add_remove(int cpu, int state)
 {
-    if ((cpu <=0) || (cpu >= vcpus)) {
-        fprintf(stderr, "vcpu out of range, should be [1~%d]\n", vcpus - 1);
+    if ((cpu <0) || (cpu >= vcpus)) {
+        fprintf(stderr, "vcpu out of range, should be [0~%d]\n", vcpus - 1);
         return;
     }
 
@@ -761,6 +761,7 @@ void qemu_cpu_add_remove(int cpu, int state)
         if (!disable_processor(&gpe_state, cpu))
             return;
     }
+    fprintf(logfile, "%s vcpu %d\n", state ? "Add" : "Remove", cpu);
 
     if (gpe_state.gpe0_en[0] & 4) {
         qemu_set_irq(sci_irq, 1);
index 89b1938c88e4f43a1dde4257885bf9c35e7d6ef7..43d30ee6c3e43dc33071e1c6c2f0020ea97122fa 100644 (file)
@@ -657,6 +657,12 @@ void xenstore_parse_domain_config(int hvm_domid)
         fprintf(logfile, "Watching %s\n", buf);
     }
 
+    /* Set a watch for vcpu-set */
+    if (pasprintf(&buf, "/local/domain/%u/cpu", domid) != -1) {
+        xs_watch(xsh, buf, "vcpu-set");
+        fprintf(logfile, "Watching %s\n", buf);
+    }
+
     /* no need for ifdef CONFIG_STUBDOM, since in the qemu case
      * hvm_domid is always equal to domid */
     hvm_domid = domid;
@@ -938,6 +944,36 @@ void xenstore_record_dm_state(const char *state)
     xenstore_record_dm("state", state);
 }
 
+static void xenstore_process_vcpu_set_event(char **vec)
+{
+    char *act = NULL;
+    char *vcpustr, *node = vec[XS_WATCH_PATH];
+    unsigned int vcpu, len;
+
+    vcpustr = strstr(node, "cpu/");
+    if (!vcpustr) {
+        fprintf(stderr, "vcpu-set: watch node error.\n");
+        return;
+    }
+    sscanf(vcpustr, "cpu/%u", &vcpu);
+
+    act = xs_read(xsh, XBT_NULL, node, &len);
+    if (!act) {
+        fprintf(stderr, "vcpu-set: no command yet.\n");
+        return;
+    }
+
+    if (!strncmp(act, "online", len))
+        qemu_cpu_add_remove(vcpu, 1);
+    else if (!strncmp(act, "offline", len))
+        qemu_cpu_add_remove(vcpu, 0);
+    else
+        fprintf(stderr, "vcpu-set: command error.\n");
+
+    free(act);
+    return;
+}
+
 void xenstore_process_event(void *opaque)
 {
     char **vec, *offset, *bpath = NULL, *buf = NULL, *drv = NULL, *image = NULL;
@@ -958,6 +994,11 @@ void xenstore_process_event(void *opaque)
         goto out;
     }
 
+    if (!strcmp(vec[XS_WATCH_TOKEN], "vcpu-set")) {
+        xenstore_process_vcpu_set_event(vec);
+        goto out;
+    }
+
     /* if we are paused don't process anything else */
     if (xen_pause_requested)
         goto out;