cpu: add cpu model support for kunpeng-920

Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
This commit is contained in:
Xu Yandong 2020-05-11 16:45:38 +08:00
parent 72e8bd75f0
commit e471c406f3
11 changed files with 1869 additions and 1 deletions

View File

@ -0,0 +1,51 @@
From efde450d2d0648475cde04f04f5e26c1a006c226 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Fri, 17 Apr 2020 14:40:27 +0800
Subject: cpu/arm: add cpu data free function to virCPUarmDataFree
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 20 ++++++++++++++++++++
1 file changed, 20 insertions(+)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index ee58021..230cd27 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -61,6 +61,25 @@ virCPUarmFeatureFree(virCPUarmFeaturePtr feature)
G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmFeature, virCPUarmFeatureFree);
+static void
+virCPUarmDataClear(virCPUarmData *data)
+{
+ if (!data)
+ return;
+
+ VIR_FREE(data->features);
+}
+
+static void
+virCPUarmDataFree(virCPUDataPtr cpuData)
+{
+ if (!cpuData)
+ return;
+
+ virCPUarmDataClear(&cpuData->data.arm);
+ VIR_FREE(cpuData);
+}
+
typedef struct _virCPUarmMap virCPUarmMap;
typedef virCPUarmMap *virCPUarmMapPtr;
struct _virCPUarmMap {
@@ -259,6 +278,7 @@ struct cpuArchDriver cpuDriverArm = {
.compare = virCPUarmCompare,
.decode = NULL,
.encode = NULL,
+ .dataFree = virCPUarmDataFree,
.baseline = virCPUarmBaseline,
.update = virCPUarmUpdate,
.validateFeatures = virCPUarmValidateFeatures,
--
2.23.0

View File

@ -0,0 +1,275 @@
From c69a629367b0e9bfa1a034301a4c3f88ad080586 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Sat, 18 Apr 2020 11:16:13 +0800
Subject: cpu/arm: add decode function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 150 ++++++++++++++++++++++++++++++++++--------
src/cpu_map/index.xml | 3 -
2 files changed, 122 insertions(+), 31 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index d85f111..eb9b1c9 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -55,7 +55,6 @@ virCPUarmFeatureFree(virCPUarmFeaturePtr feature)
return;
g_free(feature->name);
-
g_free(feature);
}
@@ -80,6 +79,8 @@ virCPUarmDataFree(virCPUDataPtr cpuData)
g_free(cpuData);
}
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUData, virCPUarmDataFree);
+
typedef struct _virCPUarmVendor virCPUarmVendor;
typedef virCPUarmVendor *virCPUarmVendorPtr;
struct _virCPUarmVendor {
@@ -103,6 +104,8 @@ virCPUarmVendorFree(virCPUarmVendorPtr vendor)
VIR_FREE(vendor);
}
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmVendor, virCPUarmVendorFree);
+
typedef struct _virCPUarmModel virCPUarmModel;
typedef virCPUarmModel *virCPUarmModelPtr;
struct _virCPUarmModel {
@@ -175,6 +178,38 @@ virCPUarmMapFree(virCPUarmMapPtr map)
G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmMap, virCPUarmMapFree);
+static virCPUarmVendorPtr
+virCPUarmVendorFindByID(virCPUarmMapPtr map,
+ unsigned long vendor_id)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (vendor->value == vendor_id)
+ return vendor;
+ }
+
+ return NULL;
+}
+
+static virCPUarmVendorPtr
+virCPUarmVendorFindByName(virCPUarmMapPtr map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (STREQ(vendor->name, name))
+ return vendor;
+ }
+
+ return NULL;
+}
+
static virCPUarmFeaturePtr
virCPUarmMapFeatureFind(virCPUarmMapPtr map,
const char *name)
@@ -213,36 +248,43 @@ virCPUarmMapFeatureParse(xmlXPathContextPtr ctxt G_GNUC_UNUSED,
return 0;
}
-static virCPUarmVendorPtr
-virCPUarmVendorFindByID(virCPUarmMapPtr map,
- unsigned long vendor_id)
+static int
+armCpuDataParseFeatures(virCPUDefPtr cpu,
+ const virCPUarmData *cpuData)
{
+ int ret = -1;
size_t i;
+ char **features;
- for (i = 0; i < map->vendors->len; i++) {
- virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+ if (!cpu || !cpuData)
+ return ret;
- if (vendor->value == vendor_id)
- return vendor;
- }
+ if (!(features = virStringSplitCount(cpuData->features, " ",
+ 0, &cpu->nfeatures)))
+ return ret;
- return NULL;
-}
+ if (cpu->nfeatures) {
+ if (VIR_ALLOC_N(cpu->features, cpu->nfeatures) < 0)
+ goto error;
-static virCPUarmVendorPtr
-virCPUarmVendorFindByName(virCPUarmMapPtr map,
- const char *name)
-{
- size_t i;
+ for (i = 0; i < cpu->nfeatures; i++) {
+ cpu->features[i].policy = VIR_CPU_FEATURE_REQUIRE;
+ cpu->features[i].name = g_strdup(features[i]);
+ }
+ }
- for (i = 0; i < map->vendors->len; i++) {
- virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+ ret = 0;
- if (STREQ(vendor->name, name))
- return vendor;
- }
+cleanup:
+ virStringListFree(features);
+ return ret;
- return NULL;
+error:
+ for (i = 0; i < cpu->nfeatures; i++)
+ VIR_FREE(cpu->features[i].name);
+ VIR_FREE(cpu->features);
+ cpu->nfeatures = 0;
+ goto cleanup;
}
static int
@@ -252,7 +294,6 @@ virCPUarmVendorParse(xmlXPathContextPtr ctxt,
{
virCPUarmMapPtr map = (virCPUarmMapPtr)data;
g_autoptr(virCPUarmVendor) vendor = NULL;
- int ret = -1;
if (virCPUarmVendorFindByName(map, name)) {
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -289,7 +330,7 @@ virCPUarmModelFindByPVR(virCPUarmMapPtr map,
for (i = 0; i < map->models->len; i++) {
virCPUarmModelPtr model = g_ptr_array_index(map->models, i);
- if (STREQ(model->pvr, pvr))
+ if (model->data.pvr == pvr)
return model;
}
@@ -299,7 +340,7 @@ virCPUarmModelFindByPVR(virCPUarmMapPtr map,
static virCPUarmModelPtr
virCPUarmModelFindByName(virCPUarmMapPtr map,
- const char *name)
+ const char *name)
{
size_t i;
@@ -321,7 +362,6 @@ virCPUarmModelParse(xmlXPathContextPtr ctxt,
virCPUarmMapPtr map = (virCPUarmMapPtr)data;
g_autoptr(virCPUarmModel) model = NULL;
char *vendor = NULL;
- int ret = -1;
if (virCPUarmModelFindByName(map, name)) {
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -404,6 +444,60 @@ virCPUarmGetMap(void)
return cpuMap;
}
+static int
+virCPUarmDecode(virCPUDefPtr cpu,
+ const virCPUarmData *cpuData,
+ virDomainCapsCPUModelsPtr models)
+{
+ virCPUarmMapPtr map;
+ virCPUarmModelPtr model;
+ virCPUarmVendorPtr vendor = NULL;
+
+ if (!cpuData || !(map = virCPUarmGetMap()))
+ return -1;
+
+ if (!(model = virCPUarmModelFindByPVR(map, cpuData->pvr))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Cannot find CPU model with PVR 0x%03lx"),
+ cpuData->pvr);
+ return -1;
+ }
+
+ if (!virCPUModelIsAllowed(model->name, models)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("CPU model %s is not supported by hypervisor"),
+ model->name);
+ return -1;
+ }
+
+ cpu->model = g_strdup(model->name);
+
+ if (cpuData->vendor_id &&
+ !(vendor = virCPUarmVendorFindByID(map, cpuData->vendor_id))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Cannot find CPU vendor with vendor id 0x%02lx"),
+ cpuData->vendor_id);
+ return -1;
+ }
+
+ if (vendor)
+ cpu->vendor = g_strdup(vendor->name);
+
+ if (cpuData->features &&
+ armCpuDataParseFeatures(cpu, cpuData) < 0)
+ return -1;
+
+ return 0;
+}
+
+static int
+virCPUarmDecodeCPUData(virCPUDefPtr cpu,
+ const virCPUData *data,
+ virDomainCapsCPUModelsPtr models)
+{
+ return virCPUarmDecode(cpu, &data->data.arm, models);
+}
+
static int
virCPUarmUpdate(virCPUDefPtr guest,
const virCPUDef *host)
@@ -432,7 +526,7 @@ virCPUarmUpdate(virCPUDefPtr guest,
guest->match = VIR_CPU_MATCH_EXACT;
ret = 0;
- cleanup:
+cleanup:
virCPUDefFree(updated);
return ret;
}
@@ -493,7 +587,7 @@ struct cpuArchDriver cpuDriverArm = {
.arch = archs,
.narch = G_N_ELEMENTS(archs),
.compare = virCPUarmCompare,
- .decode = NULL,
+ .decode = virCPUarmDecodeCPUData,
.encode = NULL,
.dataFree = virCPUarmDataFree,
.baseline = virCPUarmBaseline,
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 2e78834..985af86 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -86,9 +86,6 @@
<arch name='arm'>
<include filename='arm_features.xml'/>
- </arch>
-
- <arch name='arm'>
<include filename="arm_vendors.xml"/>
<!-- ARM-based CPU models -->
--
2.23.0

View File

@ -0,0 +1,287 @@
From a0574d45603010761d3f3034f97457fda94d2266 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Fri, 17 Apr 2020 18:13:32 +0800
Subject: cpu/arm: add load cpu map parse function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 223 +++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 220 insertions(+), 3 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index 230cd27..d85f111 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -67,7 +67,7 @@ virCPUarmDataClear(virCPUarmData *data)
if (!data)
return;
- VIR_FREE(data->features);
+ g_free(data->features);
}
static void
@@ -77,12 +77,64 @@ virCPUarmDataFree(virCPUDataPtr cpuData)
return;
virCPUarmDataClear(&cpuData->data.arm);
- VIR_FREE(cpuData);
+ g_free(cpuData);
}
+typedef struct _virCPUarmVendor virCPUarmVendor;
+typedef virCPUarmVendor *virCPUarmVendorPtr;
+struct _virCPUarmVendor {
+ char *name;
+ unsigned long value;
+};
+
+static virCPUarmVendorPtr
+virCPUarmVendorNew(void)
+{
+ return g_new0(virCPUarmVendor, 1);
+}
+
+static void
+virCPUarmVendorFree(virCPUarmVendorPtr vendor)
+{
+ if (!vendor)
+ return;
+
+ g_free(vendor->name);
+ VIR_FREE(vendor);
+}
+
+typedef struct _virCPUarmModel virCPUarmModel;
+typedef virCPUarmModel *virCPUarmModelPtr;
+struct _virCPUarmModel {
+ char *name;
+ virCPUarmVendorPtr vendor;
+ virCPUarmData data;
+};
+
+static virCPUarmModelPtr
+virCPUarmModelNew(void)
+{
+ return g_new0(virCPUarmModel, 1);
+}
+
+static void
+virCPUarmModelFree(virCPUarmModelPtr model)
+{
+ if (!model)
+ return;
+
+ virCPUarmDataClear(&model->data);
+ g_free(model->name);
+ g_free(model);
+}
+
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmModel, virCPUarmModelFree);
+
typedef struct _virCPUarmMap virCPUarmMap;
typedef virCPUarmMap *virCPUarmMapPtr;
struct _virCPUarmMap {
+ GPtrArray *vendors;
+ GPtrArray *models;
GPtrArray *features;
};
@@ -93,6 +145,14 @@ virCPUarmMapNew(void)
map = g_new0(virCPUarmMap, 1);
+ map->vendors = g_ptr_array_new();
+ g_ptr_array_set_free_func(map->vendors,
+ (GDestroyNotify) virCPUarmVendorFree);
+
+ map->models = g_ptr_array_new();
+ g_ptr_array_set_free_func(map->models,
+ (GDestroyNotify) virCPUarmModelFree);
+
map->features = g_ptr_array_new();
g_ptr_array_set_free_func(map->features,
(GDestroyNotify) virCPUarmFeatureFree);
@@ -106,6 +166,8 @@ virCPUarmMapFree(virCPUarmMapPtr map)
if (!map)
return;
+ g_ptr_array_free(map->vendors, TRUE);
+ g_ptr_array_free(map->models, TRUE);
g_ptr_array_free(map->features, TRUE);
g_free(map);
@@ -151,6 +213,161 @@ virCPUarmMapFeatureParse(xmlXPathContextPtr ctxt G_GNUC_UNUSED,
return 0;
}
+static virCPUarmVendorPtr
+virCPUarmVendorFindByID(virCPUarmMapPtr map,
+ unsigned long vendor_id)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (vendor->value == vendor_id)
+ return vendor;
+ }
+
+ return NULL;
+}
+
+static virCPUarmVendorPtr
+virCPUarmVendorFindByName(virCPUarmMapPtr map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (STREQ(vendor->name, name))
+ return vendor;
+ }
+
+ return NULL;
+}
+
+static int
+virCPUarmVendorParse(xmlXPathContextPtr ctxt,
+ const char *name,
+ void *data)
+{
+ virCPUarmMapPtr map = (virCPUarmMapPtr)data;
+ g_autoptr(virCPUarmVendor) vendor = NULL;
+ int ret = -1;
+
+ if (virCPUarmVendorFindByName(map, name)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU vendor %s already defined"), name);
+ return -1;
+ }
+
+ vendor = virCPUarmVendorNew();
+ vendor->name = g_strdup(name);
+
+ if (virXPathULongHex("string(@value)", ctxt, &vendor->value) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ "%s", _("Missing CPU vendor value"));
+ return -1;
+ }
+
+ if (virCPUarmVendorFindByID(map, vendor->value)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU vendor value 0x%2lx already defined"), vendor->value);
+ return -1;
+ }
+
+ g_ptr_array_add(map->vendors, g_steal_pointer(&vendor));
+
+ return 0;
+}
+
+static virCPUarmModelPtr
+virCPUarmModelFindByPVR(virCPUarmMapPtr map,
+ unsigned long pvr)
+{
+ size_t i;
+
+ for (i = 0; i < map->models->len; i++) {
+ virCPUarmModelPtr model = g_ptr_array_index(map->models, i);
+
+ if (STREQ(model->pvr, pvr))
+ return model;
+ }
+
+ return NULL;
+
+}
+
+static virCPUarmModelPtr
+virCPUarmModelFindByName(virCPUarmMapPtr map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->models->len; i++) {
+ virCPUarmModelPtr model = g_ptr_array_index(map->models, i);
+
+ if (STREQ(model->name, name))
+ return model;
+ }
+
+ return NULL;
+}
+
+static int
+virCPUarmModelParse(xmlXPathContextPtr ctxt,
+ const char *name,
+ void *data)
+{
+ virCPUarmMapPtr map = (virCPUarmMapPtr)data;
+ g_autoptr(virCPUarmModel) model = NULL;
+ char *vendor = NULL;
+ int ret = -1;
+
+ if (virCPUarmModelFindByName(map, name)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU model %s already defined"), name);
+ return -1;
+ }
+
+ model = virCPUarmModelNew();
+ model->name = g_strdup(name);
+
+ if (virXPathBoolean("boolean(./vendor)", ctxt)) {
+ vendor = virXPathString("string(./vendor/@name)", ctxt);
+ if (!vendor) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Invalid vendor element in CPU model %s"),
+ name);
+ return -1;
+ }
+
+ if (!(model->vendor = virCPUarmVendorFindByName(map, vendor))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown vendor %s referenced by CPU model %s"),
+ vendor, model->name);
+ return -1;
+ }
+ }
+
+ if (!virXPathBoolean("boolean(./pvr)", ctxt)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing PVR information for CPU model %s"),
+ model->name);
+ return -1;
+ }
+
+ if (virXPathULongHex("string(./pvr/@value)", ctxt, &model->data.pvr) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing or invalid PVR value in CPU model %s"),
+ model->name);
+ return -1;
+ }
+
+ g_ptr_array_add(map->models, g_steal_pointer(&model));
+
+ return 0;
+}
+
static virCPUarmMapPtr
virCPUarmLoadMap(void)
{
@@ -158,7 +375,7 @@ virCPUarmLoadMap(void)
map = virCPUarmMapNew();
- if (cpuMapLoad("arm", NULL, virCPUarmMapFeatureParse, NULL, map) < 0)
+ if (cpuMapLoad("arm", virCPUarmVendorParse, virCPUarmMapFeatureParse, virCPUarmModelParse, map) < 0)
return NULL;
return g_steal_pointer(&map);
--
2.23.0

View File

@ -0,0 +1,127 @@
From 208c9f1eb9a06d2550b7b3cfe0172840925255d4 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 20 Apr 2020 17:29:17 +0800
Subject: cpu/arm: add virCPUarmGetHost implment
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 86 +++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 86 insertions(+)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index eb9b1c9..78e604c 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -26,9 +26,15 @@
#include "cpu_map.h"
#include "virstring.h"
#include "virxml.h"
+#include "virfile.h"
#define VIR_FROM_THIS VIR_FROM_CPU
+static const char *sysinfoCpuinfo = "/proc/cpuinfo";
+
+#define CPUINFO sysinfoCpuinfo
+#define CPUINFO_FILE_LEN (1024*1024) /* 1MB limit for /proc/cpuinfo file */
+
static const virArch archs[] = {
VIR_ARCH_ARMV6L,
VIR_ARCH_ARMV7B,
@@ -531,6 +537,85 @@ cleanup:
return ret;
}
+static int
+armCpuDataFromCpuInfo(virCPUarmData *data)
+{
+ g_autofree char *str_vendor = NULL;
+ g_autofree char *str_pvr = NULL;
+ g_autofree char *outbuf = NULL;
+ char *eol = NULL;
+ const char *cur;
+
+ if (!data)
+ return -1;
+
+ if (virFileReadAll(CPUINFO, CPUINFO_FILE_LEN, &outbuf) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Failed to open %s"), CPUINFO);
+ return -1;
+ }
+
+ /* Account for format 'CPU implementer : XXXX' */
+ if ((cur = strstr(outbuf, "CPU implementer")) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("there is no \"CPU implementer\" info in %s"), CPUINFO);
+ return -1;
+ }
+
+ cur = strchr(cur, ':') + 1;
+ eol = strchr(cur, '\n');
+ virSkipSpaces(&cur);
+ if (!eol || !(str_vendor = g_strndup(cur, eol - cur)) ||
+ virStrToLong_ul(str_vendor, NULL, 16, &data->vendor_id) < 0)
+ return -1;
+
+ /* Account for format 'CPU part : XXXX' */
+ if ((cur = strstr(outbuf, "CPU part")) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("there is no \"CPU part\" info in %s"), CPUINFO);
+ return -1;
+ }
+
+ cur = strchr(cur, ':') + 1;
+ eol = strchr(cur, '\n');
+ virSkipSpaces(&cur);
+ if (!eol || !(str_pvr = g_strndup(cur, eol - cur)) ||
+ virStrToLong_ul(str_pvr, NULL, 16, &data->pvr) < 0)
+ return -1;
+
+ /* Account for format 'CPU Features : XXXX' */
+ if ((cur = strstr(outbuf, "Features")) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("there is no \"Features\" info in %s"), CPUINFO);
+ return -1;
+ }
+ cur = strchr(cur, ':') + 1;
+ eol = strchr(cur, '\n');
+ virSkipSpaces(&cur);
+ if (eol && !(data->features = g_strndup(cur, eol - cur)))
+ return -1;
+
+ return 0;
+}
+
+static int
+virCPUarmGetHost(virCPUDefPtr cpu,
+ virDomainCapsCPUModelsPtr models)
+{
+ g_autoptr(virCPUData) cpuData = NULL;
+
+ if (virCPUarmDriverInitialize() < 0)
+ return -1;
+
+ if (!(cpuData = virCPUDataNew(archs[0])))
+ return -1;
+
+ if (armCpuDataFromCpuInfo(&cpuData->data.arm) < 0)
+ return -1;
+
+ return virCPUarmDecodeCPUData(cpu, cpuData, models);
+}
+
static virCPUDefPtr
virCPUarmBaseline(virCPUDefPtr *cpus,
@@ -590,6 +675,7 @@ struct cpuArchDriver cpuDriverArm = {
.decode = virCPUarmDecodeCPUData,
.encode = NULL,
.dataFree = virCPUarmDataFree,
+ .getHost = virCPUarmGetHost,
.baseline = virCPUarmBaseline,
.update = virCPUarmUpdate,
.validateFeatures = virCPUarmValidateFeatures,
--
2.23.0

View File

@ -0,0 +1,216 @@
From 4606782bde2a6e75e88d782fc58e5db5365502c2 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 20 Apr 2020 19:17:56 +0800
Subject: cpu/arm: implment cpu baseline function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 178 ++++++++++++++++++++++++++++++++++++++++++++--
1 file changed, 174 insertions(+), 4 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index 78e604c..a7c9523 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -616,24 +616,194 @@ virCPUarmGetHost(virCPUDefPtr cpu,
return virCPUarmDecodeCPUData(cpu, cpuData, models);
}
+static void
+virCPUarmDataIntersect(virCPUarmData *data1,
+ const virCPUarmData *data2)
+{
+ char **features = NULL;
+ char **features1 = NULL;
+ char **features2 = NULL;
+ size_t count = 0;
+ size_t i;
+
+ if (!data1 || !data2)
+ return;
+
+ data1->pvr = MIN(data1->pvr, data2->pvr);
+
+ if (virStringIsEmpty(data1->features) ||
+ virStringIsEmpty(data2->features)) {
+ VIR_FREE(data1->features);
+ return;
+ }
+
+ if (STREQ_NULLABLE(data1->features, data2->features))
+ return;
+
+ if (!(features = virStringSplitCount(data1->features, " ", 0, &count)) ||
+ !(features1 = virStringSplitCount(data1->features, " ", 0, &count)) ||
+ !(features2 = virStringSplit(data2->features, " ", 0)))
+ goto cleanup;
+
+ for (i = 0; i < count; i++) {
+ if (!virStringListHasString((const char**)features2, features1[i]))
+ virStringListRemove(&features, features1[i]);
+ }
+
+ VIR_FREE(data1->features);
+ if (features)
+ data1->features = virStringListJoin((const char**)features, " ");
+
+cleanup:
+ virStringListFree(features);
+ virStringListFree(features1);
+ virStringListFree(features2);
+ return;
+}
+
+static void
+virCPUarmDataCopy(virCPUarmData *dst, const virCPUarmData *src)
+{
+ dst->features = g_strdup(src->features);
+ dst->vendor_id = src->vendor_id;
+ dst->pvr = src->pvr;
+}
+
+static virCPUarmModelPtr
+virCPUarmModelCopy(virCPUarmModelPtr model)
+{
+ g_autoptr(virCPUarmModel) copy = NULL;
+
+ copy = virCPUarmModelNew();
+
+ virCPUarmDataCopy(&copy->data, &model->data);
+ copy->name = g_strdup(model->name);
+ copy->vendor = model->vendor;
+
+ return g_steal_pointer(&copy);
+}
+
+static virCPUarmModelPtr
+virCPUarmModelFromCPU(const virCPUDef *cpu,
+ virCPUarmMapPtr map)
+{
+ g_autoptr(virCPUarmModel) model = NULL;
+ virCPUarmVendorPtr vendor = NULL;
+ char **features = NULL;
+ size_t i;
+
+ if (!cpu->model) {
+ virReportError(VIR_ERR_INVALID_ARG, "%s",
+ _("no CPU model specified"));
+ return NULL;
+ }
+
+ if (!(model = virCPUarmModelFindByName(map, cpu->model))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown CPU model %s"), cpu->model);
+ return NULL;
+ }
+
+ if (!(model = virCPUarmModelCopy(model)))
+ return NULL;
+
+ if (cpu->vendor) {
+ if (!(vendor = virCPUarmVendorFindByName(map, cpu->vendor))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown CPU vendor %s"), cpu->vendor);
+ return NULL;
+ }
+ model->data.vendor_id = vendor->value;
+ }
+
+ if (cpu->nfeatures) {
+ if (VIR_REALLOC_N(features, cpu->nfeatures + 1) < 0)
+ return model;
+
+ features[cpu->nfeatures] = NULL;
+ for (i = 0; i < cpu->nfeatures; i++)
+ features[i] = g_strdup(cpu->features[i].name);
+ VIR_FREE(model->data.features);
+ model->data.features = virStringListJoin((const char **)features, " ");
+ }
+
+ virStringListFree(features);
+ return g_steal_pointer(&model);
+}
static virCPUDefPtr
virCPUarmBaseline(virCPUDefPtr *cpus,
- unsigned int ncpus G_GNUC_UNUSED,
- virDomainCapsCPUModelsPtr models G_GNUC_UNUSED,
+ unsigned int ncpus,
+ virDomainCapsCPUModelsPtr models,
const char **features G_GNUC_UNUSED,
bool migratable G_GNUC_UNUSED)
{
- virCPUDefPtr cpu = NULL;
+ virCPUarmMapPtr map = NULL;
+ g_autoptr(virCPUDef) cpu = NULL;
+ g_autoptr(virCPUarmModel) model = NULL;
+ g_autoptr(virCPUarmModel) baseModel = NULL;
+ virCPUarmVendorPtr vendor = NULL;
+ bool outputVendor = true;
+ size_t i;
cpu = virCPUDefNew();
cpu->model = g_strdup(cpus[0]->model);
+ cpu->arch = cpus[0]->arch;
cpu->type = VIR_CPU_TYPE_GUEST;
cpu->match = VIR_CPU_MATCH_EXACT;
+ cpu->fallback = VIR_CPU_FALLBACK_FORBID;
+
+ if (!(map = virCPUarmGetMap()))
+ return NULL;
+
+ if (!(baseModel = virCPUarmModelFromCPU(cpus[0], map)))
+ return NULL;
+
+ if (!cpus[0]->vendor) {
+ outputVendor = false;
+ } else if (!(vendor = virCPUarmVendorFindByName(map, cpus[0]->vendor))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Unknown CPU vendor %s"), cpus[0]->vendor);
+ return NULL;
+ }
+
+ for (i = 0; i < ncpus; i++) {
+ const char *vn = NULL;
+ if (!(model = virCPUarmModelFromCPU(cpus[i], map)))
+ return NULL;
+
+ if (cpus[i]->vendor) {
+ vn = cpus[i]->vendor;
+ } else {
+ outputVendor = false;
+ }
+
+ if (vn) {
+ if (!vendor) {
+ if (!(vendor = virCPUarmVendorFindByName(map, vn))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Unknown CPU vendor %s"), vn);
+ return NULL;
+ }
+ } else if (STRNEQ(vendor->name, vn)) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ "%s", _("CPU vendors do not match"));
+ return NULL;
+ }
+
+ virCPUarmDataIntersect(&baseModel->data, &model->data);
+ }
+ }
+
+ if (virCPUarmDecode(cpu, &baseModel->data, models) < 0)
+ return NULL;
+
+ if (!outputVendor)
+ g_free(cpu->vendor);
- return cpu;
+ return g_steal_pointer(&cpu);
}
static virCPUCompareResult
--
2.23.0

View File

@ -0,0 +1,239 @@
From 1a70b1e3bdbd8d0dcf9281341bc23b4ff2ffaa3a Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 20 Apr 2020 19:33:49 +0800
Subject: cpu/arm: implment cpu compare function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 196 +++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 193 insertions(+), 3 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index a7c9523..3ef54b9 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -21,6 +21,7 @@
#include <config.h>
+#include "virlog.h"
#include "viralloc.h"
#include "cpu.h"
#include "cpu_map.h"
@@ -30,6 +31,8 @@
#define VIR_FROM_THIS VIR_FROM_CPU
+VIR_LOG_INIT("cpu.cpu_arm");
+
static const char *sysinfoCpuinfo = "/proc/cpuinfo";
#define CPUINFO sysinfoCpuinfo
@@ -806,14 +809,201 @@ virCPUarmBaseline(virCPUDefPtr *cpus,
return g_steal_pointer(&cpu);
}
+static bool
+virCPUarmFeaturesIsSub(char *subFeatures,
+ char *fullFeatures)
+{
+ bool ret = false;
+ char **sub = NULL;
+ char **full = NULL;
+ size_t subCount = 0;
+ size_t fullCount = 0;
+ size_t i;
+
+ if (virStringIsEmpty(subFeatures))
+ return true;
+
+ if (virStringIsEmpty(fullFeatures))
+ return ret;
+
+ if (STREQ(subFeatures, fullFeatures))
+ return true;
+
+ if (!(sub = virStringSplitCount(subFeatures, " ", 0, &subCount)) ||
+ !(full = virStringSplitCount(fullFeatures, " ", 0, &fullCount)) ||
+ subCount > fullCount)
+ goto cleanup;
+
+ for (i = 0; i < subCount; i++) {
+ if (!virStringListHasString((const char**)full, sub[i]))
+ goto cleanup;
+ }
+
+ ret = true;
+
+ cleanup:
+ virStringListFree(sub);
+ virStringListFree(full);
+ return ret;
+}
+
+static virCPUDataPtr
+armMakeCPUData(virArch arch,
+ virCPUarmData *data)
+{
+ virCPUDataPtr cpuData;
+
+ if (!(cpuData = virCPUDataNew(arch)))
+ return NULL;
+
+ virCPUarmDataCopy(&cpuData->data.arm, data);
+
+ return cpuData;
+}
+
static virCPUCompareResult
-virCPUarmCompare(virCPUDefPtr host G_GNUC_UNUSED,
- virCPUDefPtr cpu G_GNUC_UNUSED,
- bool failMessages G_GNUC_UNUSED)
+armCompute(virCPUDefPtr host,
+ virCPUDefPtr cpu,
+ virCPUDataPtr *guestData,
+ char **message)
{
+ virCPUarmMapPtr map = NULL;
+ g_autoptr(virCPUarmModel) hostModel = NULL;
+ g_autoptr(virCPUarmModel) guestModel = NULL;
+ virArch arch;
+ size_t i;
+
+ if (cpu->arch != VIR_ARCH_NONE) {
+ bool found = false;
+
+ for (i = 0; i < G_N_ELEMENTS(archs); i++) {
+ if (archs[i] == cpu->arch) {
+ found = true;
+ break;
+ }
+ }
+
+ if (!found) {
+ VIR_DEBUG("CPU arch %s does not match host arch",
+ virArchToString(cpu->arch));
+ if (message)
+ *message = g_strdup_printf(_("CPU arch %s does not match host arch"),
+ virArchToString(cpu->arch));
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+ arch = cpu->arch;
+ } else {
+ arch = host->arch;
+ }
+
+ if (cpu->vendor &&
+ (!host->vendor || STRNEQ(cpu->vendor, host->vendor))) {
+ VIR_DEBUG("host CPU vendor does not match required CPU vendor %s",
+ cpu->vendor);
+ if (message)
+ *message = g_strdup_printf(_("host CPU vendor does not match required "
+ "CPU vendor %s"),
+ cpu->vendor);
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+
+ if (!(map = virCPUarmGetMap()))
+ return VIR_CPU_COMPARE_ERROR;
+
+ /* Host CPU information */
+ if (!(hostModel = virCPUarmModelFromCPU(host, map)))
+ return VIR_CPU_COMPARE_ERROR;
+
+ if (cpu->type == VIR_CPU_TYPE_GUEST) {
+ /* Guest CPU information */
+ switch (cpu->mode) {
+ case VIR_CPU_MODE_HOST_MODEL:
+ case VIR_CPU_MODE_HOST_PASSTHROUGH:
+ /* host-model and host-passthrough:
+ * the guest CPU is the same as the host */
+ guestModel = virCPUarmModelCopy(hostModel);
+ break;
+
+ case VIR_CPU_MODE_CUSTOM:
+ /* custom:
+ * look up guest CPU information */
+ guestModel = virCPUarmModelFromCPU(cpu, map);
+ break;
+ }
+ } else {
+ /* Other host CPU information */
+ guestModel = virCPUarmModelFromCPU(cpu, map);
+ }
+
+ if (!guestModel)
+ return VIR_CPU_COMPARE_ERROR;
+
+ if (STRNEQ(guestModel->name, hostModel->name)) {
+ VIR_DEBUG("host CPU model %s does not match required CPU model %s",
+ hostModel->name, guestModel->name);
+ if (message)
+ *message = g_strdup_printf(_("host CPU model %s does not match required "
+ "CPU model %s"),
+ hostModel->name, guestModel->name);
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+
+ if (!virCPUarmFeaturesIsSub(guestModel->data.features, hostModel->data.features)) {
+ VIR_DEBUG("guest CPU features '%s' is not subset of "
+ "host CPU features '%s'",
+ guestModel->data.features, hostModel->data.features);
+ if (message)
+ *message = g_strdup_printf(_("guest CPU features '%s' is not subset of "
+ "host CPU features '%s'"),
+ guestModel->data.features,
+ hostModel->data.features);
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+
+ if (guestData &&
+ !(*guestData = armMakeCPUData(arch, &guestModel->data)))
+ return VIR_CPU_COMPARE_ERROR;
+
return VIR_CPU_COMPARE_IDENTICAL;
}
+static virCPUCompareResult
+virCPUarmCompare(virCPUDefPtr host,
+ virCPUDefPtr cpu,
+ bool failMessages)
+{
+ virCPUCompareResult ret = VIR_CPU_COMPARE_ERROR;
+ g_autofree char *message = NULL;
+
+ if (!host || !host->model) {
+ if (failMessages) {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s",
+ _("unknown host CPU"));
+ } else {
+ VIR_WARN("unknown host CPU");
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+ return VIR_CPU_COMPARE_ERROR;
+ }
+
+ ret = armCompute(host, cpu, NULL, &message);
+
+ if (failMessages && ret == VIR_CPU_COMPARE_INCOMPATIBLE) {
+ if (message) {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s", message);
+ } else {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, NULL);
+ }
+ return VIR_CPU_COMPARE_ERROR;
+ }
+
+ return ret;
+}
+
static int
virCPUarmValidateFeatures(virCPUDefPtr cpu)
{
--
2.23.0

View File

@ -0,0 +1,76 @@
From 43ebd81b60121ce002a58ebc046b19f31bb23cb6 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Thu, 16 Apr 2020 11:00:49 +0800
Subject: cpu: introduce virCPUarmData to virCPUData
introduce virCPUarmData to virCPUData union, CPUarmData include
vendor id, pvr and cpu features.
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu.h | 2 ++
src/cpu/cpu_arm_data.h | 32 ++++++++++++++++++++++++++++++++
2 files changed, 34 insertions(+)
create mode 100644 src/cpu/cpu_arm_data.h
diff --git a/src/cpu/cpu.h b/src/cpu/cpu.h
index f779d2b..ec22a18 100644
--- a/src/cpu/cpu.h
+++ b/src/cpu/cpu.h
@@ -27,6 +27,7 @@
#include "cpu_conf.h"
#include "cpu_x86_data.h"
#include "cpu_ppc64_data.h"
+#include "cpu_arm_data.h"
typedef struct _virCPUData virCPUData;
@@ -36,6 +37,7 @@ struct _virCPUData {
union {
virCPUx86Data x86;
virCPUppc64Data ppc64;
+ virCPUarmData arm;
/* generic driver needs no data */
} data;
};
diff --git a/src/cpu/cpu_arm_data.h b/src/cpu/cpu_arm_data.h
new file mode 100644
index 0000000..72b3a29
--- /dev/null
+++ b/src/cpu/cpu_arm_data.h
@@ -0,0 +1,32 @@
+/*
+ * cpu_arm_data.h: 64-bit arm CPU specific data
+ *
+ * Copyright (C) 2019. Huawei Technologies Co., Ltd. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ */
+
+#pragma once
+
+
+#define VIR_CPU_ARM_DATA_INIT { 0 }
+
+typedef struct _virCPUarmData virCPUarmData;
+struct _virCPUarmData {
+ unsigned long vendor_id;
+ unsigned long pvr;
+ char *features;
+};
--
2.23.0

View File

@ -0,0 +1,150 @@
From b305f4c05d22277ba6092bc0c2a15b752959bdec Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Thu, 16 Apr 2020 10:57:11 +0800
Subject: cpu_map: Introduce arm CPU models
Support vendor and model for virConnectGetCapabilities in ARM,
add arm cpu info to cpu map.
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu_map/Makefile.inc.am | 5 +++++
src/cpu_map/arm_Kunpeng-920.xml | 24 ++++++++++++++++++++++++
src/cpu_map/arm_cortex-a53.xml | 6 ++++++
src/cpu_map/arm_cortex-a57.xml | 6 ++++++
src/cpu_map/arm_cortex-a72.xml | 6 ++++++
src/cpu_map/arm_vendors.xml | 14 ++++++++++++++
src/cpu_map/index.xml | 12 ++++++++++++
7 files changed, 73 insertions(+)
create mode 100644 src/cpu_map/arm_Kunpeng-920.xml
create mode 100644 src/cpu_map/arm_cortex-a53.xml
create mode 100644 src/cpu_map/arm_cortex-a57.xml
create mode 100644 src/cpu_map/arm_cortex-a72.xml
create mode 100644 src/cpu_map/arm_vendors.xml
diff --git a/src/cpu_map/Makefile.inc.am b/src/cpu_map/Makefile.inc.am
index be64c9a..8663877 100644
--- a/src/cpu_map/Makefile.inc.am
+++ b/src/cpu_map/Makefile.inc.am
@@ -67,6 +67,11 @@ cpumap_DATA = \
cpu_map/x86_Skylake-Server-noTSX-IBRS.xml \
cpu_map/x86_Westmere.xml \
cpu_map/x86_Westmere-IBRS.xml \
+ cpu_map/arm_vendors.xml \
+ cpu_map/arm_cortex-a53.xml \
+ cpu_map/arm_cortex-a57.xml \
+ cpu_map/arm_cortex-a72.xml \
+ cpu_map/arm_Kunpeng-920.xml \
$(NULL)
EXTRA_DIST += $(cpumap_DATA)
diff --git a/src/cpu_map/arm_Kunpeng-920.xml b/src/cpu_map/arm_Kunpeng-920.xml
new file mode 100644
index 0000000..b681546
--- /dev/null
+++ b/src/cpu_map/arm_Kunpeng-920.xml
@@ -0,0 +1,24 @@
+<cpus>
+ <model name='Kunpeng-920'>
+ <vendor name='Hisilicon'/>
+ <pvr value='0xd01'/>
+ <feature name="fp"/>
+ <feature name="asimd"/>
+ <feature name="evtstrm"/>
+ <feature name="aes"/>
+ <feature name="pmull"/>
+ <feature name="sha1"/>
+ <feature name="sha2"/>
+ <feature name="crc32"/>
+ <feature name="atomics"/>
+ <feature name="fphp"/>
+ <feature name="asimdhp"/>
+ <feature name="cpuid"/>
+ <feature name="asimdrdm"/>
+ <feature name="jscvt"/>
+ <feature name="fcma"/>
+ <feature name="dcpop"/>
+ <feature name="asimddp"/>
+ <feature name="asimdfhm"/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_cortex-a53.xml b/src/cpu_map/arm_cortex-a53.xml
new file mode 100644
index 0000000..3580236
--- /dev/null
+++ b/src/cpu_map/arm_cortex-a53.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='cortex-a53'>
+ <vendor name='ARM'/>
+ <pvr value='0xd03'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_cortex-a57.xml b/src/cpu_map/arm_cortex-a57.xml
new file mode 100644
index 0000000..3bc4324
--- /dev/null
+++ b/src/cpu_map/arm_cortex-a57.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='cortex-a57'>
+ <vendor name='ARM'/>
+ <pvr value='0xd07'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_cortex-a72.xml b/src/cpu_map/arm_cortex-a72.xml
new file mode 100644
index 0000000..c509a40
--- /dev/null
+++ b/src/cpu_map/arm_cortex-a72.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='cortex-a72'>
+ <vendor name='ARM'/>
+ <pvr value='0xd08'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_vendors.xml b/src/cpu_map/arm_vendors.xml
new file mode 100644
index 0000000..840bf9a
--- /dev/null
+++ b/src/cpu_map/arm_vendors.xml
@@ -0,0 +1,14 @@
+<cpus>
+ <vendor name="ARM" value="0x41"/>
+ <vendor name="Broadcom" value="0x42"/>
+ <vendor name="Cavium" value="0x43"/>
+ <vendor name="DigitalEquipment" value="0x44"/>
+ <vendor name="Hisilicon" value="0x48"/>
+ <vendor name="Infineon" value="0x49"/>
+ <vendor name="Freescale" value="0x4D"/>
+ <vendor name="NVIDIA" value="0x4E"/>
+ <vendor name="APM" value="0x50"/>
+ <vendor name="Qualcomm" value="0x51"/>
+ <vendor name="Marvell" value="0x56"/>
+ <vendor name="Intel" value="0x69"/>
+</cpus>
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 50b030d..2e78834 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -87,4 +87,16 @@
<arch name='arm'>
<include filename='arm_features.xml'/>
</arch>
+
+ <arch name='arm'>
+ <include filename="arm_vendors.xml"/>
+
+ <!-- ARM-based CPU models -->
+ <include filename="arm_cortex-a53.xml"/>
+ <include filename="arm_cortex-a57.xml"/>
+ <include filename="arm_cortex-a72.xml"/>
+
+ <!-- Hisilicon-based CPU models -->
+ <include filename="arm_Kunpeng-920.xml"/>
+ </arch>
</cpus>
--
2.23.0

View File

@ -0,0 +1,263 @@
From 89b60f0cefe533a5fda021fae303e7662c141d02 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 16 Oct 2017 17:45:48 +0800
Subject: [PATCH 11/11] tests: add baseline test cases for arm CPU
add baseline test cases for aarch64
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
tests/cputest.c | 7 +++++
.../aarch64-baseline-incompatible-vendors.xml | 26 +++++++++++++++++++
...-baseline-no-compatible-feature-result.xml | 4 +++
...aarch64-baseline-no-compatible-feature.xml | 19 ++++++++++++++
.../aarch64-baseline-no-feature-result.xml | 4 +++
.../aarch64-baseline-no-feature.xml | 7 +++++
.../cputestdata/aarch64-baseline-no-model.xml | 13 ++++++++++
.../aarch64-baseline-no-vendor-result.xml | 10 +++++++
.../aarch64-baseline-no-vendor.xml | 13 ++++++++++
...baseline-one-compatible-feature-result.xml | 5 ++++
...arch64-baseline-one-compatible-feature.xml | 20 ++++++++++++++
.../aarch64-baseline-one-feature-result.xml | 5 ++++
.../aarch64-baseline-one-feature.xml | 8 ++++++
13 files changed, 141 insertions(+)
create mode 100644 tests/cputestdata/aarch64-baseline-incompatible-vendors.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-compatible-feature-result.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-compatible-feature.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-feature-result.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-feature.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-model.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-vendor-result.xml
create mode 100644 tests/cputestdata/aarch64-baseline-no-vendor.xml
create mode 100644 tests/cputestdata/aarch64-baseline-one-compatible-feature-result.xml
create mode 100644 tests/cputestdata/aarch64-baseline-one-compatible-feature.xml
create mode 100644 tests/cputestdata/aarch64-baseline-one-feature-result.xml
create mode 100644 tests/cputestdata/aarch64-baseline-one-feature.xml
diff --git a/tests/cputest.c b/tests/cputest.c
index e4b4531..3657fa4 100644
--- a/tests/cputest.c
+++ b/tests/cputest.c
@@ -1194,6 +1194,13 @@ mymain(void)
DO_TEST_BASELINE(VIR_ARCH_PPC64, "same-model", 0, 0);
DO_TEST_BASELINE(VIR_ARCH_PPC64, "legacy", 0, -1);
+ DO_TEST_BASELINE(VIR_ARCH_AARCH64, "incompatible-vendors", 0, -1);
+ DO_TEST_BASELINE(VIR_ARCH_AARCH64, "no-vendor", 0, 0);
+ DO_TEST_BASELINE(VIR_ARCH_AARCH64, "no-feature", 0, 0);
+ DO_TEST_BASELINE(VIR_ARCH_AARCH64, "one-feature", 0, 0);
+ DO_TEST_BASELINE(VIR_ARCH_AARCH64, "no-compatible-feature", 0, 0);
+ DO_TEST_BASELINE(VIR_ARCH_AARCH64, "one-compatible-feature", 0, 0);
+
/* CPU features */
DO_TEST_HASFEATURE(VIR_ARCH_X86_64, "host", "vmx", YES);
DO_TEST_HASFEATURE(VIR_ARCH_X86_64, "host", "lm", YES);
diff --git a/tests/cputestdata/aarch64-baseline-incompatible-vendors.xml b/tests/cputestdata/aarch64-baseline-incompatible-vendors.xml
new file mode 100644
index 0000000..f2c71a1
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-incompatible-vendors.xml
@@ -0,0 +1,26 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a72</model>
+ <vendor>Hisilicon</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
+</cpuTest>
diff --git a/tests/cputestdata/aarch64-baseline-no-compatible-feature-result.xml b/tests/cputestdata/aarch64-baseline-no-compatible-feature-result.xml
new file mode 100644
index 0000000..6db66aa
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-compatible-feature-result.xml
@@ -0,0 +1,4 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='forbid'>cortex-a57</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-baseline-no-compatible-feature.xml b/tests/cputestdata/aarch64-baseline-no-compatible-feature.xml
new file mode 100644
index 0000000..5fd3228
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-compatible-feature.xml
@@ -0,0 +1,19 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='pmull'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='aes'/>
+ <feature name='sha1'/>
+</cpu>
+</cpuTest>
diff --git a/tests/cputestdata/aarch64-baseline-no-feature-result.xml b/tests/cputestdata/aarch64-baseline-no-feature-result.xml
new file mode 100644
index 0000000..6db66aa
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-feature-result.xml
@@ -0,0 +1,4 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='forbid'>cortex-a57</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-baseline-no-feature.xml b/tests/cputestdata/aarch64-baseline-no-feature.xml
new file mode 100644
index 0000000..0d6af96
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-feature.xml
@@ -0,0 +1,7 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+</cpu>
+</cpuTest>
diff --git a/tests/cputestdata/aarch64-baseline-no-model.xml b/tests/cputestdata/aarch64-baseline-no-model.xml
new file mode 100644
index 0000000..6033e4c
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-model.xml
@@ -0,0 +1,13 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
+</cpuTest>
diff --git a/tests/cputestdata/aarch64-baseline-no-vendor-result.xml b/tests/cputestdata/aarch64-baseline-no-vendor-result.xml
new file mode 100644
index 0000000..c1d74c2
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-vendor-result.xml
@@ -0,0 +1,10 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='forbid'>cortex-a57</model>
+ <feature policy='require' name='fp'/>
+ <feature policy='require' name='asimd'/>
+ <feature policy='require' name='aes'/>
+ <feature policy='require' name='pmull'/>
+ <feature policy='require' name='sha1'/>
+ <feature policy='require' name='sha2'/>
+ <feature policy='require' name='crc32'/>
+</cpu>
diff --git a/tests/cputestdata/aarch64-baseline-no-vendor.xml b/tests/cputestdata/aarch64-baseline-no-vendor.xml
new file mode 100644
index 0000000..8aacb3e
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-no-vendor.xml
@@ -0,0 +1,13 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
+</cpuTest>
diff --git a/tests/cputestdata/aarch64-baseline-one-compatible-feature-result.xml b/tests/cputestdata/aarch64-baseline-one-compatible-feature-result.xml
new file mode 100644
index 0000000..84c559d
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-one-compatible-feature-result.xml
@@ -0,0 +1,5 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='forbid'>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature policy='require' name='sha1'/>
+</cpu>
diff --git a/tests/cputestdata/aarch64-baseline-one-compatible-feature.xml b/tests/cputestdata/aarch64-baseline-one-compatible-feature.xml
new file mode 100644
index 0000000..c85059b
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-one-compatible-feature.xml
@@ -0,0 +1,20 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='sha1'/>
+</cpu>
+</cpuTest>
diff --git a/tests/cputestdata/aarch64-baseline-one-feature-result.xml b/tests/cputestdata/aarch64-baseline-one-feature-result.xml
new file mode 100644
index 0000000..0fcea51
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-one-feature-result.xml
@@ -0,0 +1,5 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='forbid'>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature policy='require' name='fp'/>
+</cpu>
diff --git a/tests/cputestdata/aarch64-baseline-one-feature.xml b/tests/cputestdata/aarch64-baseline-one-feature.xml
new file mode 100644
index 0000000..e0ae15f
--- /dev/null
+++ b/tests/cputestdata/aarch64-baseline-one-feature.xml
@@ -0,0 +1,8 @@
+<cpuTest>
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+</cpu>
+</cpuTest>
--
2.23.0

View File

@ -0,0 +1,171 @@
From 8c57ff0e9b940eb1e29a4aa3e8a9d04b03424989 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 16 Oct 2017 17:55:48 +0800
Subject: tests: add cpu compare test cases for arm CPU
add cpu compare test cases for arm CPU
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
tests/cputest.c | 10 ++++++++++
.../aarch64-guest-compat-incompatible.xml | 4 ++++
tests/cputestdata/aarch64-guest-compat-none.xml | 1 +
tests/cputestdata/aarch64-guest-compat-valid.xml | 3 +++
tests/cputestdata/aarch64-guest-exact.xml | 4 ++++
tests/cputestdata/aarch64-guest-features-invalid.xml | 12 ++++++++++++
tests/cputestdata/aarch64-guest-features-valid.xml | 7 +++++++
.../aarch64-guest-legacy-incompatible.xml | 4 ++++
tests/cputestdata/aarch64-guest-legacy.xml | 4 ++++
tests/cputestdata/aarch64-guest-strict.xml | 4 ++++
tests/cputestdata/aarch64-host.xml | 12 ++++++++++++
11 files changed, 65 insertions(+)
create mode 100644 tests/cputestdata/aarch64-guest-compat-incompatible.xml
create mode 100644 tests/cputestdata/aarch64-guest-compat-none.xml
create mode 100644 tests/cputestdata/aarch64-guest-compat-valid.xml
create mode 100644 tests/cputestdata/aarch64-guest-exact.xml
create mode 100644 tests/cputestdata/aarch64-guest-features-invalid.xml
create mode 100644 tests/cputestdata/aarch64-guest-features-valid.xml
create mode 100644 tests/cputestdata/aarch64-guest-legacy-incompatible.xml
create mode 100644 tests/cputestdata/aarch64-guest-legacy.xml
create mode 100644 tests/cputestdata/aarch64-guest-strict.xml
create mode 100644 tests/cputestdata/aarch64-host.xml
diff --git a/tests/cputest.c b/tests/cputest.c
index 1f59f0d..e4b4531 100644
--- a/tests/cputest.c
+++ b/tests/cputest.c
@@ -1140,6 +1140,16 @@ mymain(void)
DO_TEST_COMPARE(VIR_ARCH_PPC64, "host", "guest-compat-invalid", VIR_CPU_COMPARE_ERROR);
DO_TEST_COMPARE(VIR_ARCH_PPC64, "host", "guest-compat-incompatible", VIR_CPU_COMPARE_INCOMPATIBLE);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-strict", VIR_CPU_COMPARE_IDENTICAL);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-exact", VIR_CPU_COMPARE_INCOMPATIBLE);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-legacy", VIR_CPU_COMPARE_IDENTICAL);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-legacy-incompatible", VIR_CPU_COMPARE_INCOMPATIBLE);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-compat-none", VIR_CPU_COMPARE_IDENTICAL);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-compat-valid", VIR_CPU_COMPARE_IDENTICAL);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-compat-incompatible", VIR_CPU_COMPARE_INCOMPATIBLE);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-features-valid", VIR_CPU_COMPARE_IDENTICAL);
+ DO_TEST_COMPARE(VIR_ARCH_AARCH64, "host", "guest-features-invalid", VIR_CPU_COMPARE_INCOMPATIBLE);
+
/* guest updates for migration
* automatically compares host CPU with the result */
DO_TEST_UPDATE(VIR_ARCH_X86_64, "host", "min", VIR_CPU_COMPARE_IDENTICAL);
diff --git a/tests/cputestdata/aarch64-guest-compat-incompatible.xml b/tests/cputestdata/aarch64-guest-compat-incompatible.xml
new file mode 100644
index 0000000..f68ead5
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-compat-incompatible.xml
@@ -0,0 +1,4 @@
+<cpu mode='custom'>
+ <model>cortex-a72</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-compat-none.xml b/tests/cputestdata/aarch64-guest-compat-none.xml
new file mode 100644
index 0000000..fd50c03
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-compat-none.xml
@@ -0,0 +1 @@
+<cpu mode='host-model'/>
diff --git a/tests/cputestdata/aarch64-guest-compat-valid.xml b/tests/cputestdata/aarch64-guest-compat-valid.xml
new file mode 100644
index 0000000..0206d6e
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-compat-valid.xml
@@ -0,0 +1,3 @@
+<cpu mode='host-model'>
+ <model>cortex-a57</model>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-exact.xml b/tests/cputestdata/aarch64-guest-exact.xml
new file mode 100644
index 0000000..bbbe65f
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-exact.xml
@@ -0,0 +1,4 @@
+<cpu match='exact'>
+ <model>cortex-a72</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-features-invalid.xml b/tests/cputestdata/aarch64-guest-features-invalid.xml
new file mode 100644
index 0000000..afbb402
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-features-invalid.xml
@@ -0,0 +1,12 @@
+<cpu>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+ <feature name='sha3'/>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-features-valid.xml b/tests/cputestdata/aarch64-guest-features-valid.xml
new file mode 100644
index 0000000..0858f76
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-features-valid.xml
@@ -0,0 +1,7 @@
+<cpu>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='crc32'/>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-legacy-incompatible.xml b/tests/cputestdata/aarch64-guest-legacy-incompatible.xml
new file mode 100644
index 0000000..2f1941d
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-legacy-incompatible.xml
@@ -0,0 +1,4 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='allow'>cortex-a72</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-legacy.xml b/tests/cputestdata/aarch64-guest-legacy.xml
new file mode 100644
index 0000000..64a05e4
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-legacy.xml
@@ -0,0 +1,4 @@
+<cpu mode='custom' match='exact'>
+ <model fallback='allow'>cortex-a57</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-guest-strict.xml b/tests/cputestdata/aarch64-guest-strict.xml
new file mode 100644
index 0000000..a057ebd
--- /dev/null
+++ b/tests/cputestdata/aarch64-guest-strict.xml
@@ -0,0 +1,4 @@
+<cpu match='strict'>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+</cpu>
diff --git a/tests/cputestdata/aarch64-host.xml b/tests/cputestdata/aarch64-host.xml
new file mode 100644
index 0000000..60c20f2
--- /dev/null
+++ b/tests/cputestdata/aarch64-host.xml
@@ -0,0 +1,12 @@
+<cpu>
+ <arch>aarch64</arch>
+ <model>cortex-a57</model>
+ <vendor>ARM</vendor>
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+</cpu>
--
2.23.0

View File

@ -99,7 +99,7 @@
Summary: Library providing a simple virtualization API Summary: Library providing a simple virtualization API
Name: libvirt Name: libvirt
Version: 6.2.0 Version: 6.2.0
Release: 2 Release: 3
License: LGPLv2+ License: LGPLv2+
URL: https://libvirt.org/ URL: https://libvirt.org/
@ -113,6 +113,16 @@ Patch0002: libvirt-qemu-fix-a-concurrent-operation-situation.patch
Patch0003: libvirt-cgroup-cleanup-eventParams-when-virTypedParamsAddULL.patch Patch0003: libvirt-cgroup-cleanup-eventParams-when-virTypedParamsAddULL.patch
Patch0004: libvirt-nodedev-fix-potential-heap-use-after-free.patch Patch0004: libvirt-nodedev-fix-potential-heap-use-after-free.patch
Patch0005: libvirt-po-Refresh-translation-for-running-state.patch Patch0005: libvirt-po-Refresh-translation-for-running-state.patch
Patch0006: libvirt-cpu_map-Introduce-arm-CPU-models.patch
Patch0007: libvirt-cpu-introduce-virCPUarmData-to-virCPUData.patch
Patch0008: libvirt-cpu-arm-add-cpu-data-free-function-to-virCPUarmDataF.patch
Patch0009: libvirt-cpu-arm-add-load-cpu-map-parse-function.patch
Patch0010: libvirt-cpu-arm-add-decode-function.patch
Patch0011: libvirt-cpu-arm-add-virCPUarmGetHost-implment.patch
Patch0012: libvirt-cpu-arm-implment-cpu-baseline-function.patch
Patch0013: libvirt-cpu-arm-implment-cpu-compare-function.patch
Patch0014: libvirt-tests-add-cpu-compare-test-cases-for-arm-CPU.patch
Patch0015: libvirt-tests-add-baseline-test-cases-for-arm-CPU.patch
Requires: libvirt-daemon = %{version}-%{release} Requires: libvirt-daemon = %{version}-%{release}
@ -1846,6 +1856,9 @@ exit 0
%changelog %changelog
* Mon May 11 2020 Xu Yandong <xuyandong2@huawei.com> - 6.2.0-3
- Checkout cpu capabilities support for ARM architecture.
- Support Kunpeng-920 CPU.
* Mon Apr 20 2020 Xu Yandong <xuyandong2@huawei.com> - 6.2.0-2 * Mon Apr 20 2020 Xu Yandong <xuyandong2@huawei.com> - 6.2.0-2
- Checkout bugfixs from 5.5.0 release. - Checkout bugfixs from 5.5.0 release.
* Tue Apr 14 2020 Xu Yandong <xuyandong2@huawei.com> - 6.2.0-1 * Tue Apr 14 2020 Xu Yandong <xuyandong2@huawei.com> - 6.2.0-1