]> xenbits.xensource.com Git - people/vhanquez/xen-unstable.git/commitdiff
Extend cpupools to support numa
authorJuergen Gross <juergen.gross@ts.fujitsu.com>
Thu, 9 Dec 2010 10:26:37 +0000 (11:26 +0100)
committerJuergen Gross <juergen.gross@ts.fujitsu.com>
Thu, 9 Dec 2010 10:26:37 +0000 (11:26 +0100)
The user interfaces for cpupools are extended to support numa machines:
- xl cpupool-create supports now specifying a node list instead of a cpu list.
  The new cpupool will be created with all free cpus of the specified numa
  nodes.
- xl cpupool-cpu-remove and xl cpupool-cpu-add can take a node number instead
  of a cpu number. Using 'node:1' for the cpu parameter will, depending on
  the operation, either remove all cpus of node 1 in the specified cpupool,
  or add all free cpus of node 1 to the cpupool.

libxl is extended with the following functions to support this feature:
int libxl_cpupool_cpuadd_node(libxl_ctx *ctx, uint32_t poolid, int node, int *cpus)
int libxl_cpupool_cpuremove_node(libxl_ctx *ctx, uint32_t poolid, int node, int *cpus)

Signed-off-by: juergen.gross@ts.fujitsu.com
Signed-off-by: Ian Jackson <ian.jackson.citrix.com>
tools/libxl/libxl.c
tools/libxl/libxl.h
tools/libxl/xl_cmdimpl.c
tools/libxl/xl_cmdtable.c

index 4be8b8f988476fbcdd9d90cd21ccb692a00e3b18..6436ada8f22f70288a87634ea811746dfdd0cba3 100644 (file)
@@ -3898,6 +3898,38 @@ int libxl_cpupool_cpuadd(libxl_ctx *ctx, uint32_t poolid, int cpu)
     return 0;
 }
 
+int libxl_cpupool_cpuadd_node(libxl_ctx *ctx, uint32_t poolid, int node, int *cpus)
+{
+    int rc = 0;
+    int cpu;
+    libxl_cpumap freemap;
+    libxl_topologyinfo topology;
+
+    if (libxl_get_freecpus(ctx, &freemap)) {
+        return ERROR_FAIL;
+    }
+
+    if (libxl_get_topologyinfo(ctx, &topology)) {
+        rc = ERROR_FAIL;
+        goto out;
+    }
+
+    *cpus = 0;
+    for (cpu = 0; cpu < topology.nodemap.entries; cpu++) {
+        if (libxl_cpumap_test(&freemap, cpu) &&
+            (topology.nodemap.array[cpu] == node) &&
+            !libxl_cpupool_cpuadd(ctx, poolid, cpu)) {
+                (*cpus)++;
+        }
+    }
+
+    libxl_topologyinfo_destroy(&topology);
+
+out:
+    libxl_cpumap_destroy(&freemap);
+    return rc;
+}
+
 int libxl_cpupool_cpuremove(libxl_ctx *ctx, uint32_t poolid, int cpu)
 {
     int rc;
@@ -3911,6 +3943,48 @@ int libxl_cpupool_cpuremove(libxl_ctx *ctx, uint32_t poolid, int cpu)
     return 0;
 }
 
+int libxl_cpupool_cpuremove_node(libxl_ctx *ctx, uint32_t poolid, int node, int *cpus)
+{
+    int ret = 0;
+    int n_pools;
+    int p;
+    int cpu;
+    libxl_topologyinfo topology;
+    libxl_cpupoolinfo *poolinfo;
+
+    poolinfo = libxl_list_cpupool(ctx, &n_pools);
+    if (!poolinfo) {
+        return ERROR_NOMEM;
+    }
+
+    if (libxl_get_topologyinfo(ctx, &topology)) {
+        ret = ERROR_FAIL;
+        goto out;
+    }
+
+    *cpus = 0;
+    for (p = 0; p < n_pools; p++) {
+        if (poolinfo[p].poolid == poolid) {
+            for (cpu = 0; cpu < topology.nodemap.entries; cpu++) {
+                if ((topology.nodemap.array[cpu] == node) &&
+                    libxl_cpumap_test(&poolinfo[p].cpumap, cpu) &&
+                    !libxl_cpupool_cpuremove(ctx, poolid, cpu)) {
+                        (*cpus)++;
+                }
+            }
+        }
+    }
+
+    libxl_topologyinfo_destroy(&topology);
+
+out:
+    for (p = 0; p < n_pools; p++) {
+        libxl_cpupoolinfo_destroy(poolinfo + p);
+    }
+
+    return ret;
+}
+
 int libxl_cpupool_movedomain(libxl_ctx *ctx, uint32_t poolid, uint32_t domid)
 {
     libxl__gc gc = LIBXL_INIT_GC(ctx);
index 63fb9f9a13edcbb15e9acbf69db1054cdeaa9510..e763665c8ae5862b214cc9a1e01e2d0f47927ca5 100644 (file)
@@ -529,7 +529,9 @@ int libxl_create_cpupool(libxl_ctx *ctx, const char *name, int schedid,
                          uint32_t *poolid);
 int libxl_destroy_cpupool(libxl_ctx *ctx, uint32_t poolid);
 int libxl_cpupool_cpuadd(libxl_ctx *ctx, uint32_t poolid, int cpu);
+int libxl_cpupool_cpuadd_node(libxl_ctx *ctx, uint32_t poolid, int node, int *cpus);
 int libxl_cpupool_cpuremove(libxl_ctx *ctx, uint32_t poolid, int cpu);
+int libxl_cpupool_cpuremove_node(libxl_ctx *ctx, uint32_t poolid, int node, int *cpus);
 int libxl_cpupool_movedomain(libxl_ctx *ctx, uint32_t poolid, uint32_t domid);
 
 /* common paths */
index 55970aeb2a70ac08bce4757152a8d456a796cfe1..9c14d60438d96328e825673cc5341671b4318180 100644 (file)
@@ -5412,10 +5412,12 @@ int main_cpupoolcreate(int argc, char **argv)
     uint32_t poolid;
     int schedid = -1;
     XLU_ConfigList *cpus;
-    int n_cpus, i, n;
+    XLU_ConfigList *nodes;
+    int n_cpus, n_nodes, i, n;
     libxl_cpumap freemap;
     libxl_cpumap cpumap;
     libxl_uuid uuid;
+    libxl_topologyinfo topology;
 
     while (1) {
         opt = getopt_long(argc, argv, "hnf:", long_options, &option_index);
@@ -5524,7 +5526,32 @@ int main_cpupoolcreate(int argc, char **argv)
         fprintf(stderr, "Failed to allocate cpumap\n");
         return -ERROR_FAIL;
     }
-    if (!xlu_cfg_get_list(config, "cpus", &cpus, 0, 0)) {
+    if (!xlu_cfg_get_list(config, "nodes", &nodes, 0, 0)) {
+        n_cpus = 0;
+        n_nodes = 0;
+        if (libxl_get_topologyinfo(&ctx, &topology)) {
+            fprintf(stderr, "libxl_get_topologyinfo failed\n");
+            return -ERROR_FAIL;
+        }
+        while ((buf = xlu_cfg_get_listitem(nodes, n_nodes)) != NULL) {
+            n = atoi(buf);
+            for (i = 0; i < topology.nodemap.entries; i++) {
+                if ((topology.nodemap.array[i] == n) &&
+                    libxl_cpumap_test(&freemap, i)) {
+                    libxl_cpumap_set(&cpumap, i);
+                    n_cpus++;
+                }
+            }
+            n_nodes++;
+        }
+
+        libxl_topologyinfo_destroy(&topology);
+
+        if (n_cpus == 0) {
+            fprintf(stderr, "no free cpu found\n");
+            return -ERROR_FAIL;
+        }
+    } else if (!xlu_cfg_get_list(config, "cpus", &cpus, 0, 0)) {
         n_cpus = 0;
         while ((buf = xlu_cfg_get_listitem(cpus, n_cpus)) != NULL) {
             i = atoi(buf);
@@ -5708,6 +5735,8 @@ int main_cpupoolcpuadd(int argc, char **argv)
     const char *pool;
     uint32_t poolid;
     int cpu;
+    int node;
+    int n;
 
     while ((opt = getopt(argc, argv, "h")) != -1) {
         switch (opt) {
@@ -5732,7 +5761,13 @@ int main_cpupoolcpuadd(int argc, char **argv)
         help("cpupool-cpu-add");
         return -ERROR_FAIL;
     }
-    cpu = atoi(argv[optind]);
+    node = -1;
+    cpu = -1;
+    if (strncmp(argv[optind], "node:", 5) == 0) {
+        node = atoi(argv[optind] + 5);
+    } else {
+        cpu = atoi(argv[optind]);
+    }
 
     if (cpupool_qualifier_to_cpupoolid(pool, &poolid, NULL) ||
         !libxl_cpupoolid_to_name(&ctx, poolid)) {
@@ -5740,7 +5775,21 @@ int main_cpupoolcpuadd(int argc, char **argv)
         return -ERROR_FAIL;
     }
 
-    return -libxl_cpupool_cpuadd(&ctx, poolid, cpu);
+    if (cpu >= 0) {
+        return -libxl_cpupool_cpuadd(&ctx, poolid, cpu);
+    }
+
+    if (libxl_cpupool_cpuadd_node(&ctx, poolid, node, &n)) {
+        fprintf(stderr, "libxl_cpupool_cpuadd_node failed\n");
+        return -ERROR_FAIL;
+    }
+
+    if (n > 0) {
+        return 0;
+    }
+
+    fprintf(stderr, "no free cpu found\n");
+    return -ERROR_FAIL;
 }
 
 int main_cpupoolcpuremove(int argc, char **argv)
@@ -5749,6 +5798,8 @@ int main_cpupoolcpuremove(int argc, char **argv)
     const char *pool;
     uint32_t poolid;
     int cpu;
+    int node;
+    int n;
 
     while ((opt = getopt(argc, argv, "h")) != -1) {
         switch (opt) {
@@ -5773,7 +5824,13 @@ int main_cpupoolcpuremove(int argc, char **argv)
         help("cpupool-cpu-remove");
         return -ERROR_FAIL;
     }
-    cpu = atoi(argv[optind]);
+    node = -1;
+    cpu = -1;
+    if (strncmp(argv[optind], "node:", 5) == 0) {
+        node = atoi(argv[optind] + 5);
+    } else {
+        cpu = atoi(argv[optind]);
+    }
 
     if (cpupool_qualifier_to_cpupoolid(pool, &poolid, NULL) ||
         !libxl_cpupoolid_to_name(&ctx, poolid)) {
@@ -5781,7 +5838,21 @@ int main_cpupoolcpuremove(int argc, char **argv)
         return -ERROR_FAIL;
     }
 
-    return -libxl_cpupool_cpuremove(&ctx, poolid, cpu);
+    if (cpu >= 0) {
+        return -libxl_cpupool_cpuremove(&ctx, poolid, cpu);
+    }
+
+    if (libxl_cpupool_cpuremove_node(&ctx, poolid, node, &n)) {
+        fprintf(stderr, "libxl_cpupool_cpuremove_node failed\n");
+        return -ERROR_FAIL;
+    }
+
+    if (n == 0) {
+        fprintf(stderr, "no cpu of node found in cpupool\n");
+        return -ERROR_FAIL;
+    }
+
+    return 0;
 }
 
 int main_cpupoolmigrate(int argc, char **argv)
index 149bce978f7bf3be9728f411021ebeb2c532e20b..0da6077becbf0a89268783a3245d36139d8b0e08 100644 (file)
@@ -361,12 +361,12 @@ struct cmd_spec cmd_table[] = {
     { "cpupool-cpu-add",
       &main_cpupoolcpuadd,
       "Adds a CPU to a CPU pool",
-      "<CPU Pool> <CPU nr>",
+      "<CPU Pool> <CPU nr>|node:<node nr>",
     },
     { "cpupool-cpu-remove",
       &main_cpupoolcpuremove,
       "Removes a CPU from a CPU pool",
-      "<CPU Pool> <CPU nr>",
+      "<CPU Pool> <CPU nr>|node:<node nr>",
     },
     { "cpupool-migrate",
       &main_cpupoolmigrate,