From patchwork Tue Sep 6 15:15:20 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cornelia Huck X-Patchwork-Id: 9317267 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id EB28D601C0 for ; Tue, 6 Sep 2016 15:24:38 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 13F4628DCC for ; Tue, 6 Sep 2016 15:24:39 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 08B9E28DE9; Tue, 6 Sep 2016 15:24:39 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.9 required=2.0 tests=BAYES_00,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id B5DD628DCC for ; Tue, 6 Sep 2016 15:24:37 +0000 (UTC) Received: from localhost ([::1]:34339 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bhIEm-0004jl-60 for patchwork-qemu-devel@patchwork.kernel.org; Tue, 06 Sep 2016 11:24:36 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:34342) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bhI69-0006QT-K2 for qemu-devel@nongnu.org; Tue, 06 Sep 2016 11:15:46 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1bhI61-0000i2-St for qemu-devel@nongnu.org; Tue, 06 Sep 2016 11:15:40 -0400 Received: from mx0a-001b2d01.pphosted.com ([148.163.156.1]:43349) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1bhI61-0000hr-Ih for qemu-devel@nongnu.org; Tue, 06 Sep 2016 11:15:33 -0400 Received: from pps.filterd (m0098404.ppops.net [127.0.0.1]) by mx0a-001b2d01.pphosted.com (8.16.0.17/8.16.0.17) with SMTP id u86FDXfD132670 for ; Tue, 6 Sep 2016 11:15:30 -0400 Received: from e06smtp14.uk.ibm.com (e06smtp14.uk.ibm.com [195.75.94.110]) by mx0a-001b2d01.pphosted.com with ESMTP id 259w3j5c30-1 (version=TLSv1.2 cipher=AES256-SHA bits=256 verify=NOT) for ; Tue, 06 Sep 2016 11:15:30 -0400 Received: from localhost by e06smtp14.uk.ibm.com with IBM ESMTP SMTP Gateway: Authorized Use Only! Violators will be prosecuted for from ; Tue, 6 Sep 2016 16:15:26 +0100 Received: from d06dlp01.portsmouth.uk.ibm.com (9.149.20.13) by e06smtp14.uk.ibm.com (192.168.101.144) with IBM ESMTP SMTP Gateway: Authorized Use Only! Violators will be prosecuted; Tue, 6 Sep 2016 16:15:23 +0100 X-IBM-Helo: d06dlp01.portsmouth.uk.ibm.com X-IBM-MailFrom: cornelia.huck@de.ibm.com X-IBM-RcptTo: qemu-devel@nongnu.org Received: from b06cxnps3075.portsmouth.uk.ibm.com (d06relay10.portsmouth.uk.ibm.com [9.149.109.195]) by d06dlp01.portsmouth.uk.ibm.com (Postfix) with ESMTP id 4FD8C17D8024 for ; Tue, 6 Sep 2016 16:17:15 +0100 (BST) Received: from d06av05.portsmouth.uk.ibm.com (d06av05.portsmouth.uk.ibm.com [9.149.37.229]) by b06cxnps3075.portsmouth.uk.ibm.com (8.14.9/8.14.9/NCO v10.0) with ESMTP id u86FFNu428639430 for ; Tue, 6 Sep 2016 15:15:23 GMT Received: from d06av05.portsmouth.uk.ibm.com (localhost [127.0.0.1]) by d06av05.portsmouth.uk.ibm.com (8.14.4/8.14.4/NCO v10.0 AVout) with ESMTP id u86FFMKM002653 for ; Tue, 6 Sep 2016 09:15:23 -0600 Received: from gondolin.boeblingen.de.ibm.com (dyn-9-152-224-137.boeblingen.de.ibm.com [9.152.224.137]) by d06av05.portsmouth.uk.ibm.com (8.14.4/8.14.4/NCO v10.0 AVin) with ESMTP id u86FFL6T002592 (version=TLSv1/SSLv3 cipher=AES256-SHA256 bits=256 verify=NO); Tue, 6 Sep 2016 09:15:22 -0600 From: Cornelia Huck To: peter.maydell@linaro.org Date: Tue, 6 Sep 2016 17:15:20 +0200 X-Mailer: git-send-email 2.9.3 In-Reply-To: <20160906151520.26977-1-cornelia.huck@de.ibm.com> References: <20160906151520.26977-1-cornelia.huck@de.ibm.com> X-TM-AS-MML: disable X-Content-Scanned: Fidelis XPS MAILER x-cbid: 16090615-0016-0000-0000-0000022CFCD6 X-IBM-AV-DETECTION: SAVI=unused REMOTE=unused XFE=unused x-cbparentid: 16090615-0017-0000-0000-000022E2EF88 Message-Id: <20160906151520.26977-2-cornelia.huck@de.ibm.com> X-Proofpoint-Virus-Version: vendor=fsecure engine=2.50.10432:, , definitions=2016-09-06_05:, , signatures=0 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 spamscore=0 suspectscore=3 malwarescore=0 phishscore=0 adultscore=0 bulkscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.0.1-1604210000 definitions=main-1609060236 X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x [generic] X-Received-From: 148.163.156.1 Subject: [Qemu-devel] [PULL v2 11/38] s390x/cpumodel: "host" and "qemu" as CPU subclasses X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: borntraeger@de.ibm.com, agraf@suse.de, qemu-devel@nongnu.org, David Hildenbrand , jfrei@linux.vnet.ibm.com, Cornelia Huck Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP From: David Hildenbrand This patch introduces two CPU models, "host" and "qemu". "qemu" is used as default when running under TCG. "host" is used as default when running under KVM. "host" cannot be used without KVM. "host" is not migration-safe. They both inherit from the base s390x CPU, which is turned into an abstract class. This patch also changes CPU creation to take care of the passed CPU string and reuses common code parse_features() function for that purpose. Unknown CPU definitions are now reported. The "-cpu ?" and "query-cpu-definition" commands are changed to list all CPU subclasses automatically, including migration-safety and whether static. Acked-by: Cornelia Huck Signed-off-by: David Hildenbrand Message-Id: <20160905085244.99980-3-dahi@linux.vnet.ibm.com> [CH: fix up self-assignments in s390_cpu_list, as spotted by clang] Signed-off-by: Cornelia Huck --- hw/s390x/s390-virtio.c | 6 +- target-s390x/Makefile.objs | 2 +- target-s390x/cpu-qom.h | 4 + target-s390x/cpu.c | 33 ++------- target-s390x/cpu.h | 2 + target-s390x/cpu_models.c | 177 +++++++++++++++++++++++++++++++++++++++++++++ target-s390x/helper.c | 33 ++++++++- 7 files changed, 229 insertions(+), 28 deletions(-) create mode 100644 target-s390x/cpu_models.c diff --git a/hw/s390x/s390-virtio.c b/hw/s390x/s390-virtio.c index 544c616..0a96347 100644 --- a/hw/s390x/s390-virtio.c +++ b/hw/s390x/s390-virtio.c @@ -101,7 +101,11 @@ void s390_init_cpus(MachineState *machine) gchar *name; if (machine->cpu_model == NULL) { - machine->cpu_model = "host"; + if (kvm_enabled()) { + machine->cpu_model = "host"; + } else { + machine->cpu_model = "qemu"; + } } cpu_states = g_new0(S390CPU *, max_cpus); diff --git a/target-s390x/Makefile.objs b/target-s390x/Makefile.objs index dd62cbd..34bd693 100644 --- a/target-s390x/Makefile.objs +++ b/target-s390x/Makefile.objs @@ -1,5 +1,5 @@ obj-y += translate.o helper.o cpu.o interrupt.o obj-y += int_helper.o fpu_helper.o cc_helper.o mem_helper.o misc_helper.o -obj-y += gdbstub.o +obj-y += gdbstub.o cpu_models.o obj-$(CONFIG_SOFTMMU) += machine.o ioinst.o arch_dump.o mmu_helper.o obj-$(CONFIG_KVM) += kvm.o diff --git a/target-s390x/cpu-qom.h b/target-s390x/cpu-qom.h index 66b5d18..bb993d4 100644 --- a/target-s390x/cpu-qom.h +++ b/target-s390x/cpu-qom.h @@ -45,6 +45,10 @@ typedef struct S390CPUClass { /*< private >*/ CPUClass parent_class; /*< public >*/ + bool kvm_required; + bool is_static; + bool is_migration_safe; + const char *desc; int64_t next_cpu_id; diff --git a/target-s390x/cpu.c b/target-s390x/cpu.c index e43e2d6..44e53ec 100644 --- a/target-s390x/cpu.c +++ b/target-s390x/cpu.c @@ -44,30 +44,6 @@ #define CR0_RESET 0xE0UL #define CR14_RESET 0xC2000000UL; -/* generate CPU information for cpu -? */ -void s390_cpu_list(FILE *f, fprintf_function cpu_fprintf) -{ -#ifdef CONFIG_KVM - (*cpu_fprintf)(f, "s390 %16s\n", "host"); -#endif -} - -#ifndef CONFIG_USER_ONLY -CpuDefinitionInfoList *arch_query_cpu_definitions(Error **errp) -{ - CpuDefinitionInfoList *entry; - CpuDefinitionInfo *info; - - info = g_malloc0(sizeof(*info)); - info->name = g_strdup("host"); - - entry = g_malloc0(sizeof(*entry)); - entry->value = info; - - return entry; -} -#endif - static void s390_cpu_set_pc(CPUState *cs, vaddr value) { S390CPU *cpu = S390_CPU(cs); @@ -206,6 +182,12 @@ static void s390_cpu_realizefn(DeviceState *dev, Error **errp) CPUS390XState *env = &cpu->env; Error *err = NULL; + /* the model has to be realized before qemu_init_vcpu() due to kvm */ + s390_realize_cpu_model(cs, &err); + if (err) { + goto out; + } + #if !defined(CONFIG_USER_ONLY) if (cpu->id >= max_cpus) { error_setg(&err, "Unable to add CPU: %" PRIi64 @@ -435,6 +417,7 @@ static void s390_cpu_class_init(ObjectClass *oc, void *data) scc->cpu_reset = s390_cpu_reset; scc->initial_cpu_reset = s390_cpu_initial_reset; cc->reset = s390_cpu_full_reset; + cc->class_by_name = s390_cpu_class_by_name, cc->has_work = s390_cpu_has_work; cc->do_interrupt = s390_cpu_do_interrupt; cc->dump_state = s390_cpu_dump_state; @@ -470,7 +453,7 @@ static const TypeInfo s390_cpu_type_info = { .instance_size = sizeof(S390CPU), .instance_init = s390_cpu_initfn, .instance_finalize = s390_cpu_finalize, - .abstract = false, + .abstract = true, .class_size = sizeof(S390CPUClass), .class_init = s390_cpu_class_init, }; diff --git a/target-s390x/cpu.h b/target-s390x/cpu.h index eeff1b0..0ea9321 100644 --- a/target-s390x/cpu.h +++ b/target-s390x/cpu.h @@ -633,6 +633,8 @@ extern void subsystem_reset(void); void s390_cpu_list(FILE *f, fprintf_function cpu_fprintf); #define cpu_list s390_cpu_list +void s390_realize_cpu_model(CPUState *cs, Error **errp); +ObjectClass *s390_cpu_class_by_name(const char *name); #define EXCP_EXT 1 /* external interrupt */ #define EXCP_SVC 2 /* supervisor call (syscall) */ diff --git a/target-s390x/cpu_models.c b/target-s390x/cpu_models.c new file mode 100644 index 0000000..49969e8 --- /dev/null +++ b/target-s390x/cpu_models.c @@ -0,0 +1,177 @@ +/* + * CPU models for s390x + * + * Copyright 2016 IBM Corp. + * + * Author(s): David Hildenbrand + * + * This work is licensed under the terms of the GNU GPL, version 2 or (at + * your option) any later version. See the COPYING file in the top-level + * directory. + */ + +#include "qemu/osdep.h" +#include "cpu.h" +#include "qapi/error.h" +#ifndef CONFIG_USER_ONLY +#include "sysemu/arch_init.h" +#endif + +struct S390PrintCpuListInfo { + FILE *f; + fprintf_function print; +}; + +static void print_cpu_model_list(ObjectClass *klass, void *opaque) +{ + struct S390PrintCpuListInfo *info = opaque; + S390CPUClass *scc = S390_CPU_CLASS(klass); + char *name = g_strdup(object_class_get_name(klass)); + const char *details = ""; + + if (scc->is_static) { + details = "(static, migration-safe)"; + } else if (scc->is_migration_safe) { + details = "(migration-safe)"; + } + + /* strip off the -s390-cpu */ + g_strrstr(name, "-" TYPE_S390_CPU)[0] = 0; + (*info->print)(info->f, "s390 %-15s %-35s %s\n", name, scc->desc, + details); + g_free(name); +} + +void s390_cpu_list(FILE *f, fprintf_function print) +{ + struct S390PrintCpuListInfo info = { + .f = f, + .print = print, + }; + + object_class_foreach(print_cpu_model_list, TYPE_S390_CPU, false, &info); +} + +#ifndef CONFIG_USER_ONLY +static void create_cpu_model_list(ObjectClass *klass, void *opaque) +{ + CpuDefinitionInfoList **cpu_list = opaque; + CpuDefinitionInfoList *entry; + CpuDefinitionInfo *info; + char *name = g_strdup(object_class_get_name(klass)); + S390CPUClass *scc = S390_CPU_CLASS(klass); + + /* strip off the -s390-cpu */ + g_strrstr(name, "-" TYPE_S390_CPU)[0] = 0; + info = g_malloc0(sizeof(*info)); + info->name = name; + info->has_migration_safe = true; + info->migration_safe = scc->is_migration_safe; + info->q_static = scc->is_static; + + + entry = g_malloc0(sizeof(*entry)); + entry->value = info; + entry->next = *cpu_list; + *cpu_list = entry; +} + +CpuDefinitionInfoList *arch_query_cpu_definitions(Error **errp) +{ + CpuDefinitionInfoList *list = NULL; + + object_class_foreach(create_cpu_model_list, TYPE_S390_CPU, false, &list); + + return list; +} +#endif + +void s390_realize_cpu_model(CPUState *cs, Error **errp) +{ + S390CPUClass *xcc = S390_CPU_GET_CLASS(cs); + + if (xcc->kvm_required && !kvm_enabled()) { + error_setg(errp, "CPU definition requires KVM"); + return; + } +} + +#ifdef CONFIG_KVM +static void s390_host_cpu_model_initfn(Object *obj) +{ +} +#endif + +static void s390_qemu_cpu_model_initfn(Object *obj) +{ +} + +static void s390_cpu_model_finalize(Object *obj) +{ +} + +#ifdef CONFIG_KVM +static void s390_host_cpu_model_class_init(ObjectClass *oc, void *data) +{ + S390CPUClass *xcc = S390_CPU_CLASS(oc); + + xcc->kvm_required = true; + xcc->desc = "KVM only: All recognized features"; +} +#endif + +static void s390_qemu_cpu_model_class_init(ObjectClass *oc, void *data) +{ + S390CPUClass *xcc = S390_CPU_CLASS(oc); + + xcc->is_migration_safe = true; + xcc->desc = g_strdup_printf("QEMU Virtual CPU version %s", + qemu_hw_version()); +} + +#define S390_CPU_TYPE_SUFFIX "-" TYPE_S390_CPU +#define S390_CPU_TYPE_NAME(name) (name S390_CPU_TYPE_SUFFIX) + +/* Generate type name for a cpu model. Caller has to free the string. */ +static char *s390_cpu_type_name(const char *model_name) +{ + return g_strdup_printf(S390_CPU_TYPE_NAME("%s"), model_name); +} + +ObjectClass *s390_cpu_class_by_name(const char *name) +{ + char *typename = s390_cpu_type_name(name); + ObjectClass *oc; + + oc = object_class_by_name(typename); + g_free(typename); + return oc; +} + +static const TypeInfo qemu_s390_cpu_type_info = { + .name = S390_CPU_TYPE_NAME("qemu"), + .parent = TYPE_S390_CPU, + .instance_init = s390_qemu_cpu_model_initfn, + .instance_finalize = s390_cpu_model_finalize, + .class_init = s390_qemu_cpu_model_class_init, +}; + +#ifdef CONFIG_KVM +static const TypeInfo host_s390_cpu_type_info = { + .name = S390_CPU_TYPE_NAME("host"), + .parent = TYPE_S390_CPU, + .instance_init = s390_host_cpu_model_initfn, + .instance_finalize = s390_cpu_model_finalize, + .class_init = s390_host_cpu_model_class_init, +}; +#endif + +static void register_types(void) +{ + type_register_static(&qemu_s390_cpu_type_info); +#ifdef CONFIG_KVM + type_register_static(&host_s390_cpu_type_info); +#endif +} + +type_init(register_types) diff --git a/target-s390x/helper.c b/target-s390x/helper.c index 54a5177..68bd2f9 100644 --- a/target-s390x/helper.c +++ b/target-s390x/helper.c @@ -70,7 +70,38 @@ void s390x_cpu_timer(void *opaque) S390CPU *cpu_s390x_create(const char *cpu_model, Error **errp) { - return S390_CPU(object_new(TYPE_S390_CPU)); + static bool features_parsed; + char *name, *features; + const char *typename; + ObjectClass *oc; + CPUClass *cc; + + name = g_strdup(cpu_model); + features = strchr(name, ','); + if (features) { + features[0] = 0; + features++; + } + + oc = cpu_class_by_name(TYPE_S390_CPU, name); + if (!oc) { + error_setg(errp, "Unknown CPU definition \'%s\'", name); + g_free(name); + return NULL; + } + typename = object_class_get_name(oc); + + if (!features_parsed) { + features_parsed = true; + cc = CPU_CLASS(oc); + cc->parse_features(typename, features, errp); + } + g_free(name); + + if (*errp) { + return NULL; + } + return S390_CPU(CPU(object_new(typename))); } S390CPU *s390x_new_cpu(const char *cpu_model, int64_t id, Error **errp)