提交 bfb412a3 编写于 作者: D Daniel P. Berrange

nodeinfo: split CPU info retrieval out of nodeGetInfo

Instead of having platform specific code in nodeGetInfo to
fetch CPU topology, split it all out into a new method
nodeGetCPUInfo.
Signed-off-by: NDaniel P. Berrange <berrange@redhat.com>
上级 3050a3f5
...@@ -608,14 +608,19 @@ nodeHasValidSubcoreConfiguration(int threads_per_subcore) ...@@ -608,14 +608,19 @@ nodeHasValidSubcoreConfiguration(int threads_per_subcore)
int int
linuxNodeInfoCPUPopulate(FILE *cpuinfo, linuxNodeInfoCPUPopulate(FILE *cpuinfo,
virArch arch, virArch arch,
virNodeInfoPtr nodeinfo) unsigned int *cpus,
unsigned int *mhz,
unsigned int *nodes,
unsigned int *sockets,
unsigned int *cores,
unsigned int *threads)
{ {
virBitmapPtr present_cpus_map = NULL; virBitmapPtr present_cpus_map = NULL;
virBitmapPtr online_cpus_map = NULL; virBitmapPtr online_cpus_map = NULL;
char line[1024]; char line[1024];
DIR *nodedir = NULL; DIR *nodedir = NULL;
struct dirent *nodedirent = NULL; struct dirent *nodedirent = NULL;
int cpus, cores, socks, threads, offline = 0; int nodecpus, nodecores, nodesockets, nodethreads, offline = 0;
int threads_per_subcore = 0; int threads_per_subcore = 0;
unsigned int node; unsigned int node;
int ret = -1; int ret = -1;
...@@ -623,6 +628,9 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -623,6 +628,9 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
char *sysfs_cpudir = NULL; char *sysfs_cpudir = NULL;
int direrr; int direrr;
*mhz = 0;
*cpus = *nodes = *sockets = *cores = *threads = 0;
/* Start with parsing CPU clock speed from /proc/cpuinfo */ /* Start with parsing CPU clock speed from /proc/cpuinfo */
while (fgets(line, sizeof(line), cpuinfo) != NULL) { while (fgets(line, sizeof(line), cpuinfo) != NULL) {
if (ARCH_IS_X86(arch)) { if (ARCH_IS_X86(arch)) {
...@@ -644,9 +652,8 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -644,9 +652,8 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
if (virStrToLong_ui(buf+1, &p, 10, &ui) == 0 && if (virStrToLong_ui(buf+1, &p, 10, &ui) == 0 &&
/* Accept trailing fractional part. */ /* Accept trailing fractional part. */
(*p == '\0' || *p == '.' || c_isspace(*p))) (*p == '\0' || *p == '.' || c_isspace(*p)))
nodeinfo->mhz = ui; *mhz = ui;
} }
} else if (ARCH_IS_PPC(arch)) { } else if (ARCH_IS_PPC(arch)) {
char *buf = line; char *buf = line;
if (STRPREFIX(buf, "clock")) { if (STRPREFIX(buf, "clock")) {
...@@ -666,7 +673,7 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -666,7 +673,7 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
if (virStrToLong_ui(buf+1, &p, 10, &ui) == 0 && if (virStrToLong_ui(buf+1, &p, 10, &ui) == 0 &&
/* Accept trailing fractional part. */ /* Accept trailing fractional part. */
(*p == '\0' || *p == '.' || c_isspace(*p))) (*p == '\0' || *p == '.' || c_isspace(*p)))
nodeinfo->mhz = ui; *mhz = ui;
/* No other interesting infos are available in /proc/cpuinfo. /* No other interesting infos are available in /proc/cpuinfo.
* However, there is a line identifying processor's version, * However, there is a line identifying processor's version,
* identification and machine, but we don't want it to be caught * identification and machine, but we don't want it to be caught
...@@ -692,12 +699,12 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -692,12 +699,12 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
if (virStrToLong_ui(buf+1, &p, 10, &ui) == 0 if (virStrToLong_ui(buf+1, &p, 10, &ui) == 0
/* Accept trailing fractional part. */ /* Accept trailing fractional part. */
&& (*p == '\0' || *p == '.' || c_isspace(*p))) && (*p == '\0' || *p == '.' || c_isspace(*p)))
nodeinfo->mhz = ui; *mhz = ui;
} }
} else if (ARCH_IS_S390(arch)) { } else if (ARCH_IS_S390(arch)) {
/* s390x has no realistic value for CPU speed, /* s390x has no realistic value for CPU speed,
* assign a value of zero to signify this */ * assign a value of zero to signify this */
nodeinfo->mhz = 0; *mhz = 0;
} else { } else {
VIR_WARN("Parser for /proc/cpuinfo needs to be adapted for your architecture"); VIR_WARN("Parser for /proc/cpuinfo needs to be adapted for your architecture");
break; break;
...@@ -758,38 +765,38 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -758,38 +765,38 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
if (sscanf(nodedirent->d_name, "node%u", &node) != 1) if (sscanf(nodedirent->d_name, "node%u", &node) != 1)
continue; continue;
nodeinfo->nodes++; (*nodes)++;
if (virAsprintf(&sysfs_cpudir, "%s/node/%s", if (virAsprintf(&sysfs_cpudir, "%s/node/%s",
sysfs_system_path, nodedirent->d_name) < 0) sysfs_system_path, nodedirent->d_name) < 0)
goto cleanup; goto cleanup;
if ((cpus = virNodeParseNode(sysfs_cpudir, arch, if ((nodecpus = virNodeParseNode(sysfs_cpudir, arch,
present_cpus_map, present_cpus_map,
online_cpus_map, online_cpus_map,
threads_per_subcore, threads_per_subcore,
&socks, &cores, &nodesockets, &nodecores,
&threads, &offline)) < 0) &nodethreads, &offline)) < 0)
goto cleanup; goto cleanup;
VIR_FREE(sysfs_cpudir); VIR_FREE(sysfs_cpudir);
nodeinfo->cpus += cpus; *cpus += nodecpus;
if (socks > nodeinfo->sockets) if (nodesockets > *sockets)
nodeinfo->sockets = socks; *sockets = nodesockets;
if (cores > nodeinfo->cores) if (nodecores > *cores)
nodeinfo->cores = cores; *cores = nodecores;
if (threads > nodeinfo->threads) if (nodethreads > *threads)
nodeinfo->threads = threads; *threads = nodethreads;
} }
if (direrr < 0) if (direrr < 0)
goto cleanup; goto cleanup;
if (nodeinfo->cpus && nodeinfo->nodes) if (*cpus && *nodes)
goto done; goto done;
fallback: fallback:
...@@ -798,33 +805,33 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -798,33 +805,33 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
if (virAsprintf(&sysfs_cpudir, "%s/cpu", sysfs_system_path) < 0) if (virAsprintf(&sysfs_cpudir, "%s/cpu", sysfs_system_path) < 0)
goto cleanup; goto cleanup;
if ((cpus = virNodeParseNode(sysfs_cpudir, arch, if ((nodecpus = virNodeParseNode(sysfs_cpudir, arch,
present_cpus_map, present_cpus_map,
online_cpus_map, online_cpus_map,
threads_per_subcore, threads_per_subcore,
&socks, &cores, &nodesockets, &nodecores,
&threads, &offline)) < 0) &nodethreads, &offline)) < 0)
goto cleanup; goto cleanup;
nodeinfo->nodes = 1; *nodes = 1;
nodeinfo->cpus = cpus; *cpus = nodecpus;
nodeinfo->sockets = socks; *sockets = nodesockets;
nodeinfo->cores = cores; *cores = nodecores;
nodeinfo->threads = threads; *threads = nodethreads;
done: done:
/* There should always be at least one cpu, socket, node, and thread. */ /* There should always be at least one cpu, socket, node, and thread. */
if (nodeinfo->cpus == 0) { if (*cpus == 0) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("no CPUs found")); virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("no CPUs found"));
goto cleanup; goto cleanup;
} }
if (nodeinfo->sockets == 0) { if (*sockets == 0) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("no sockets found")); virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("no sockets found"));
goto cleanup; goto cleanup;
} }
if (nodeinfo->threads == 0) { if (*threads == 0) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("no threads found")); virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("no threads found"));
goto cleanup; goto cleanup;
} }
...@@ -836,14 +843,14 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo, ...@@ -836,14 +843,14 @@ linuxNodeInfoCPUPopulate(FILE *cpuinfo,
* the nodeinfo structure isn't designed to carry the full topology so * the nodeinfo structure isn't designed to carry the full topology so
* we're going to lie about the detected topology to notify the user * we're going to lie about the detected topology to notify the user
* to check the host capabilities for the actual topology. */ * to check the host capabilities for the actual topology. */
if ((nodeinfo->nodes * if ((*nodes *
nodeinfo->sockets * *sockets *
nodeinfo->cores * *cores *
nodeinfo->threads) != (nodeinfo->cpus + offline)) { *threads) != (*cpus + offline)) {
nodeinfo->nodes = 1; *nodes = 1;
nodeinfo->sockets = 1; *sockets = 1;
nodeinfo->cores = nodeinfo->cpus + offline; *cores = *cpus + offline;
nodeinfo->threads = 1; *threads = 1;
} }
ret = 0; ret = 0;
...@@ -1161,23 +1168,17 @@ virNodeGetSiblingsList(const char *dir, int cpu_id) ...@@ -1161,23 +1168,17 @@ virNodeGetSiblingsList(const char *dir, int cpu_id)
} }
#endif #endif
int
nodeGetInfo(virNodeInfoPtr nodeinfo)
{
virArch hostarch = virArchFromHost();
unsigned long long memorybytes;
memset(nodeinfo, 0, sizeof(*nodeinfo));
if (virStrcpyStatic(nodeinfo->model, virArchToString(hostarch)) == NULL)
return -1;
if (nodeGetMemory(&memorybytes, NULL) < 0)
return -1;
nodeinfo->memory = memorybytes / 1024;
static int
nodeGetCPUInfo(virArch hostarch,
unsigned int *cpus,
unsigned int *mhz,
unsigned int *nodes,
unsigned int *sockets,
unsigned int *cores,
unsigned int *threads)
{
#ifdef __linux__ #ifdef __linux__
{
int ret = -1; int ret = -1;
FILE *cpuinfo = fopen(CPUINFO_PATH, "r"); FILE *cpuinfo = fopen(CPUINFO_PATH, "r");
...@@ -1187,28 +1188,27 @@ nodeGetInfo(virNodeInfoPtr nodeinfo) ...@@ -1187,28 +1188,27 @@ nodeGetInfo(virNodeInfoPtr nodeinfo)
return -1; return -1;
} }
ret = linuxNodeInfoCPUPopulate(cpuinfo, hostarch, nodeinfo); ret = linuxNodeInfoCPUPopulate(cpuinfo, hostarch,
cpus, mhz, nodes,
sockets, cores, threads);
if (ret < 0) if (ret < 0)
goto cleanup; goto cleanup;
cleanup: cleanup:
VIR_FORCE_FCLOSE(cpuinfo); VIR_FORCE_FCLOSE(cpuinfo);
return ret; return ret;
}
#elif defined(__FreeBSD__) || defined(__APPLE__) #elif defined(__FreeBSD__) || defined(__APPLE__)
{ unsigned long cpu_freq;
nodeinfo->nodes = 1; size_t cpu_freq_len = sizeof(cpu_freq);
nodeinfo->sockets = 1;
nodeinfo->threads = 1;
nodeinfo->cpus = appleFreebsdNodeGetCPUCount(); *cpus = appleFreebsdNodeGetCPUCount();
if (nodeinfo->cpus == -1) if (*cpus == -1)
return -1; return -1;
nodeinfo->cores = nodeinfo->cpus; *nodes = 1;
*sockets = 1;
unsigned long cpu_freq; *cores = *cpus;
size_t cpu_freq_len = sizeof(cpu_freq); *threads = 1;
# ifdef __FreeBSD__ # ifdef __FreeBSD__
if (sysctlbyname("dev.cpu.0.freq", &cpu_freq, &cpu_freq_len, NULL, 0) < 0) { if (sysctlbyname("dev.cpu.0.freq", &cpu_freq, &cpu_freq_len, NULL, 0) < 0) {
...@@ -1216,18 +1216,17 @@ nodeGetInfo(virNodeInfoPtr nodeinfo) ...@@ -1216,18 +1216,17 @@ nodeGetInfo(virNodeInfoPtr nodeinfo)
return -1; return -1;
} }
nodeinfo->mhz = cpu_freq; *mhz = cpu_freq;
# else # else
if (sysctlbyname("hw.cpufrequency", &cpu_freq, &cpu_freq_len, NULL, 0) < 0) { if (sysctlbyname("hw.cpufrequency", &cpu_freq, &cpu_freq_len, NULL, 0) < 0) {
virReportSystemError(errno, "%s", _("cannot obtain CPU freq")); virReportSystemError(errno, "%s", _("cannot obtain CPU freq"));
return -1; return -1;
} }
nodeinfo->mhz = cpu_freq / 1000000; *mhz = cpu_freq / 1000000;
# endif # endif
return 0; return 0;
}
#else #else
/* XXX Solaris will need an impl later if they port QEMU driver */ /* XXX Solaris will need an impl later if they port QEMU driver */
virReportError(VIR_ERR_NO_SUPPORT, "%s", virReportError(VIR_ERR_NO_SUPPORT, "%s",
...@@ -1236,6 +1235,31 @@ nodeGetInfo(virNodeInfoPtr nodeinfo) ...@@ -1236,6 +1235,31 @@ nodeGetInfo(virNodeInfoPtr nodeinfo)
#endif #endif
} }
int
nodeGetInfo(virNodeInfoPtr nodeinfo)
{
virArch hostarch = virArchFromHost();
unsigned long long memorybytes;
memset(nodeinfo, 0, sizeof(*nodeinfo));
if (virStrcpyStatic(nodeinfo->model, virArchToString(hostarch)) == NULL)
return -1;
if (nodeGetMemory(&memorybytes, NULL) < 0)
return -1;
nodeinfo->memory = memorybytes / 1024;
if (nodeGetCPUInfo(hostarch,
&nodeinfo->cpus, &nodeinfo->mhz,
&nodeinfo->nodes, &nodeinfo->sockets,
&nodeinfo->cores, &nodeinfo->threads) < 0)
return -1;
return 0;
}
int int
nodeGetCPUStats(int cpuNum ATTRIBUTE_UNUSED, nodeGetCPUStats(int cpuNum ATTRIBUTE_UNUSED,
virNodeCPUStatsPtr params ATTRIBUTE_UNUSED, virNodeCPUStatsPtr params ATTRIBUTE_UNUSED,
......
...@@ -29,7 +29,12 @@ void linuxNodeInfoSetSysFSSystemPath(const char *path); ...@@ -29,7 +29,12 @@ void linuxNodeInfoSetSysFSSystemPath(const char *path);
int linuxNodeInfoCPUPopulate(FILE *cpuinfo, int linuxNodeInfoCPUPopulate(FILE *cpuinfo,
virArch arch, virArch arch,
virNodeInfoPtr nodeinfo); unsigned int *cpus,
unsigned int *mhz,
unsigned int *nodes,
unsigned int *sockets,
unsigned int *cores,
unsigned int *threads);
int linuxNodeGetCPUStats(FILE *procstat, int linuxNodeGetCPUStats(FILE *procstat,
int cpuNum, int cpuNum,
......
...@@ -41,7 +41,10 @@ linuxTestCompareFiles(const char *cpuinfofile, ...@@ -41,7 +41,10 @@ linuxTestCompareFiles(const char *cpuinfofile,
} }
memset(&nodeinfo, 0, sizeof(nodeinfo)); memset(&nodeinfo, 0, sizeof(nodeinfo));
if (linuxNodeInfoCPUPopulate(cpuinfo, arch, &nodeinfo) < 0) { if (linuxNodeInfoCPUPopulate(cpuinfo, arch,
&nodeinfo.cpus, &nodeinfo.mhz,
&nodeinfo.nodes, &nodeinfo.sockets,
&nodeinfo.cores, &nodeinfo.threads) < 0) {
if (virTestGetDebug()) { if (virTestGetDebug()) {
if (virGetLastError()) if (virGetLastError())
VIR_TEST_DEBUG("\n%s\n", virGetLastErrorMessage()); VIR_TEST_DEBUG("\n%s\n", virGetLastErrorMessage());
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册