VIR_DEBUG("model=%s", NULLSTR(cpu->model));
return 0;
}
+
+
+/**
+ * virCPUConvertLegacy:
+ *
+ * @arch: CPU architecture
+ * @cpu: CPU definition to be converted
+ *
+ * Convert legacy CPU definition into one that the corresponding cpu driver
+ * will be able to work with. Currently this is only implemented by the PPC
+ * driver, which needs to convert legacy POWERx_v* names into POWERx.
+ *
+ * Returns -1 on error, 0 on success.
+ */
+int
+virCPUConvertLegacy(virArch arch,
+ virCPUDefPtr cpu)
+{
+ struct cpuArchDriver *driver;
+
+ VIR_DEBUG("arch=%s, cpu=%p, model=%s",
+ virArchToString(arch), cpu, NULLSTR(cpu->model));
+
+ if (!(driver = cpuGetSubDriver(arch)))
+ return -1;
+
+ if (!driver->convertLegacy)
+ return 0;
+
+ if (driver->convertLegacy(cpu) < 0)
+ return -1;
+
+ VIR_DEBUG("model=%s", NULLSTR(cpu->model));
+ return 0;
+}
const char **models,
unsigned int nmodels);
+typedef int
+(*virCPUArchConvertLegacy)(virCPUDefPtr cpu);
+
struct cpuArchDriver {
const char *name;
const virArch *arch;
virCPUArchDataParse dataParse;
virCPUArchGetModels getModels;
virCPUArchTranslate translate;
+ virCPUArchConvertLegacy convertLegacy;
};
unsigned int nmodels)
ATTRIBUTE_NONNULL(2);
+int
+virCPUConvertLegacy(virArch arch,
+ virCPUDefPtr cpu)
+ ATTRIBUTE_NONNULL(2);
/* virCPUDataFormat and virCPUDataParse are implemented for unit tests only and
* have no real-life usage
* POWER7_v2.3 => POWER7
* POWER7+_v2.1 => POWER7
* POWER8_v1.0 => POWER8 */
-static virCPUDefPtr
-ppc64ConvertLegacyCPUDef(const virCPUDef *legacy)
+static int
+virCPUppc64ConvertLegacy(virCPUDefPtr cpu)
{
- virCPUDefPtr cpu;
-
- if (!(cpu = virCPUDefCopy(legacy)))
- goto out;
-
- if (!cpu->model ||
- !(STREQ(cpu->model, "POWER7_v2.1") ||
- STREQ(cpu->model, "POWER7_v2.3") ||
- STREQ(cpu->model, "POWER7+_v2.1") ||
- STREQ(cpu->model, "POWER8_v1.0"))) {
- goto out;
+ if (cpu->model &&
+ (STREQ(cpu->model, "POWER7_v2.1") ||
+ STREQ(cpu->model, "POWER7_v2.3") ||
+ STREQ(cpu->model, "POWER7+_v2.1") ||
+ STREQ(cpu->model, "POWER8_v1.0"))) {
+ cpu->model[strlen("POWERx")] = 0;
}
- cpu->model[strlen("POWERx")] = 0;
-
- out:
- return cpu;
+ return 0;
}
/* Some hosts can run guests in compatibility mode, but not all
size_t i;
/* Ensure existing configurations are handled correctly */
- if (!(cpu = ppc64ConvertLegacyCPUDef(other)))
+ if (!(cpu = virCPUDefCopy(other)) ||
+ virCPUppc64ConvertLegacy(cpu) < 0)
goto cleanup;
if (cpu->arch != VIR_ARCH_NONE) {
.baseline = ppc64DriverBaseline,
.update = virCPUppc64Update,
.getModels = virCPUppc64DriverGetModels,
+ .convertLegacy = virCPUppc64ConvertLegacy,
};
virCPUCheckFeature;
virCPUCompare;
virCPUCompareXML;
+virCPUConvertLegacy;
virCPUDataCheckFeature;
virCPUDataFormat;
virCPUDataParse;
return -1;
}
+ if (virCPUConvertLegacy(caps->host.arch, def->cpu) < 0)
+ return -1;
+
/* nothing to update for host-passthrough */
if (def->cpu->mode == VIR_CPU_MODE_HOST_PASSTHROUGH)
return 0;
!(cpu = cpuTestLoadXML(data->arch, data->name)))
goto cleanup;
+ if (virCPUConvertLegacy(host->arch, cpu) < 0)
+ goto cleanup;
+
cmpResult = virCPUCompare(host->arch, host, cpu, false);
if (cmpResult == VIR_CPU_COMPARE_ERROR ||
cmpResult == VIR_CPU_COMPARE_INCOMPATIBLE) {
DO_TEST_GUESTCPU("ppc64", "host", "guest", ppc_models, 0);
DO_TEST_GUESTCPU("ppc64", "host", "guest-nofallback", ppc_models, -1);
- DO_TEST_GUESTCPU("ppc64", "host", "guest-legacy", ppc_models, /*0*/ -1);
+ DO_TEST_GUESTCPU("ppc64", "host", "guest-legacy", ppc_models, 0);
DO_TEST_GUESTCPU("ppc64", "host", "guest-legacy-incompatible", ppc_models, -1);
DO_TEST_GUESTCPU("ppc64", "host", "guest-legacy-invalid", ppc_models, -1);