From 77c830d8c44695ffaec29523bf01cee2364e42ef Mon Sep 17 00:00:00 2001 From: Michal Privoznik Date: Mon, 2 Jun 2014 12:06:56 +0200 Subject: [PATCH] virnuma: Introduce virNumaGetDistances The API gets a NUMA node and find distances to other nodes. The distances are returned in an array. If an item X within the array equals to value of zero, then there's no such node as X. Signed-off-by: Michal Privoznik --- src/libvirt_private.syms | 1 + src/util/virnuma.c | 55 ++++++++++++++++++++++++++++++++++++++++ src/util/virnuma.h | 3 +++ 3 files changed, 59 insertions(+) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 4c1f61cefc..d73a9f5100 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1652,6 +1652,7 @@ virNodeSuspendGetTargetMask; virDomainNumatuneMemModeTypeFromString; virDomainNumatuneMemModeTypeToString; virNumaGetAutoPlacementAdvice; +virNumaGetDistances; virNumaGetMaxNode; virNumaGetNodeMemory; virNumaIsAvailable; diff --git a/src/util/virnuma.c b/src/util/virnuma.c index 1e099eb403..e8ceec8530 100644 --- a/src/util/virnuma.c +++ b/src/util/virnuma.c @@ -216,6 +216,61 @@ virNumaGetMaxNode(void) } +/** + * virNumaGetDistances: + * @node: identifier of the requested NUMA node + * @distances: array of distances to sibling nodes + * @ndistances: size of @distances + * + * Get array of distances to sibling nodes from @node. If a + * distances[x] equals to zero, the node x is not enabled or + * doesn't exist. As a special case, if @node itself refers to + * disabled or nonexistent NUMA node, then @distances and + * @ndistances are set to NULL and zero respectively. + * + * The distances are a bit of magic. For a local node the value + * is 10, for remote it's typically 20 meaning that time penalty + * for accessing a remote node is two time bigger than when + * accessing a local node. + * + * Returns 0 on success, -1 otherwise. + */ +int +virNumaGetDistances(int node, + int **distances, + int *ndistances) +{ + int ret = -1; + int max_node; + size_t i; + + if (!numa_bitmask_isbitset(numa_nodes_ptr, node)) { + VIR_DEBUG("Node %d does not exist", node); + *distances = NULL; + *ndistances = 0; + return 0; + } + + if ((max_node = virNumaGetMaxNode()) < 0) + goto cleanup; + + if (VIR_ALLOC_N(*distances, max_node) < 0) + goto cleanup; + + *ndistances = max_node + 1; + + for (i = 0; i<= max_node; i++) { + if (!numa_bitmask_isbitset(numa_nodes_ptr, i)) + continue; + + (*distances)[i] = numa_distance(node, i); + } + + ret = 0; + cleanup: + return ret; +} + /** * virNumaGetNodeMemory: * @node: identifier of the requested NUMA node diff --git a/src/util/virnuma.h b/src/util/virnuma.h index 8464b19538..fe1e9667cc 100644 --- a/src/util/virnuma.h +++ b/src/util/virnuma.h @@ -58,6 +58,9 @@ int virNumaSetupMemoryPolicy(virNumaTuneDef numatune, bool virNumaIsAvailable(void); int virNumaGetMaxNode(void); +int virNumaGetDistances(int node, + int **distances, + int *ndistances); int virNumaGetNodeMemory(int node, unsigned long long *memsize, unsigned long long *memfree); -- GitLab