2 * virnumamock.c: Mock some virNuma functions using sysfs
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library. If not, see
16 * <http://www.gnu.org/licenses/>.
26 #include "virstring.h"
28 #define VIR_FROM_THIS VIR_FROM_NONE
30 #define SYSFS_SYSTEM_PATH "/sys/devices/system"
32 static int numa_avail
= -1;
36 * Poor man's mocked NUMA guesser. We basically check if
37 * /sys/devices/system/node (where /sys/devices/system can already be mocked or
38 * changed in the tests) exists and cache the result.
41 virNumaIsAvailable(void)
44 char *sysfs_node_path
= NULL
;
46 if (virAsprintfQuiet(&sysfs_node_path
, "%s/node", SYSFS_SYSTEM_PATH
) < 0)
49 numa_avail
= virFileExists(sysfs_node_path
);
51 VIR_FREE(sysfs_node_path
);
55 * Quite a few more things need to be mocked if NUMA is not available and
56 * you are using this file. Do not remove the abort() call below unless you
57 * make sure all under virCapabilitiesInitNUMAFake() is mocked (and whatever
58 * might have changed since this comment was added. You are welcome.
67 virNumaGetMaxNode(void)
70 virBitmapPtr map
= NULL
;
72 if (virFileReadValueBitmap(&map
, "%s/node/online", SYSFS_SYSTEM_PATH
) < 0)
75 ret
= virBitmapLastSetBit(map
);
81 virNumaNodeIsAvailable(int node
)
84 virBitmapPtr map
= NULL
;
86 if (virFileReadValueBitmap(&map
, "%s/node/online", SYSFS_SYSTEM_PATH
) < 0)
89 ret
= virBitmapIsBitSet(map
, node
);
95 virNumaGetNodeMemory(int node
,
96 unsigned long long *memsize
,
97 unsigned long long *memfree
)
99 const unsigned long long base
= 1 << 30;
102 *memsize
= base
* (node
+ 1);
111 virNumaGetDistances(int node ATTRIBUTE_UNUSED
,
121 * TODO: Adapt virNumaGetHugePageInfo{Path,Dir} to use sysfs so that the
122 * paths can be modified and this function can be thrown away and instead we'd
123 * have copied info from /sys (as we do with /sys/devices/system).
126 virNumaGetPages(int node
,
127 unsigned int **pages_size
,
128 unsigned long long **pages_avail
,
129 unsigned long long **pages_free
,
132 const int pages_def
[] = { 4, 2 * 1024, 1 * 1024 * 1024};
133 const int npages_def
= ARRAY_CARDINALITY(pages_def
);
147 if ((pages_size
&& VIR_ALLOC_N(*pages_size
, npages_def
) < 0) ||
148 (pages_avail
&& VIR_ALLOC_N(*pages_avail
, npages_def
) < 0) ||
149 (pages_free
&& VIR_ALLOC_N(*pages_free
, npages_def
) < 0)) {
150 VIR_FREE(*pages_size
);
151 VIR_FREE(*pages_avail
);
155 *npages
= npages_def
;
157 memcpy(*pages_size
, pages_def
, sizeof(pages_def
));
163 if (pages_avail
|| pages_free
) {
164 for (i
= 0; i
< *npages
; i
++) {
166 (*pages_avail
)[i
] = (node
+ i
) * 2 << 10;
168 (*pages_free
)[i
] = (node
+ i
) * 1 << 10;
176 virNumaGetNodeCPUs(int node
, virBitmapPtr
*cpus
)
179 char *cpulist
= NULL
;
181 if (virFileReadValueString(&cpulist
,
182 "%s/node/node%u/cpulist",
183 SYSFS_SYSTEM_PATH
, node
) < 0)
186 *cpus
= virBitmapParseUnlimited(cpulist
);
190 ret
= virBitmapCountBits(*cpus
);