From nobody Mon Feb 9 12:47:54 2026 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1733484360; cv=none; d=zohomail.com; s=zohoarc; b=Qn0aL6NPLOhO7cX2E1a0Y2lIqObPOn9sWrtBykTuXJJS90bxiriWFxORv9OgCr4z4lwdothSdAP6Hjvweb18/3X1RazkCQVCXqjRP+AX5lTRtOHJ+8YXgguIvn0p9+g0ThRtxEsWtmME1pjM7nJ7HvNj2c4c7ktmMqkaPm9CAlw= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1733484360; h=Content-Type:Content-Transfer-Encoding:Cc:Cc:Date:Date:From:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:Subject:To:To:Message-Id:Reply-To; bh=AS3dhdTtX8nlhECXlD2WH8GMfczxIljzgWd6E4YGRlU=; b=R/76T1uatdBzGpE69LW7MgpL/Tvo+c1Ks1zgUsylrHrpLrlneZ6TcdQ6bHSyfyvxM+KRRJ831QZ4x3DxzQcjmQFEvgUVslNaS5GEAScOj/JtXHNsdgW+jCHT3uzE6FLdSUvr3dt6gdCBQSkQZQUc9tS4U/FesYRyKbriL45EZa4= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass header.from= (p=none dis=none) Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1733484360903663.2282441915362; Fri, 6 Dec 2024 03:26:00 -0800 (PST) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1tJWT3-0005O6-OJ; Fri, 06 Dec 2024 06:25:54 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1tJWRb-0003nk-JE for qemu-devel@nongnu.org; Fri, 06 Dec 2024 06:24:25 -0500 Received: from us-smtp-delivery-124.mimecast.com ([170.10.129.124]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1tJWRZ-00028b-Qn for qemu-devel@nongnu.org; Fri, 06 Dec 2024 06:24:23 -0500 Received: from mx-prod-mc-05.mail-002.prod.us-west-2.aws.redhat.com (ec2-54-186-198-63.us-west-2.compute.amazonaws.com [54.186.198.63]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-467-DvuFZHtZPDepWhL3oQg9xA-1; Fri, 06 Dec 2024 06:24:17 -0500 Received: from mx-prod-int-03.mail-002.prod.us-west-2.aws.redhat.com (mx-prod-int-03.mail-002.prod.us-west-2.aws.redhat.com [10.30.177.12]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by mx-prod-mc-05.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTPS id 8B2971956046; Fri, 6 Dec 2024 11:24:15 +0000 (UTC) Received: from gondolin.str.redhat.com (dhcp-192-244.str.redhat.com [10.33.192.244]) by mx-prod-int-03.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTP id 9FC0919560AD; Fri, 6 Dec 2024 11:24:09 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1733484261; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=AS3dhdTtX8nlhECXlD2WH8GMfczxIljzgWd6E4YGRlU=; b=cGACe0/6Cs8LR6gX5Bo4ArXkjFD6jNBp+GbjStab02wtx7KBSt6B1yL4RmmQT6H6/SXhq2 GvzBhB3Wr1lzZGUDS5YqN4RtczATVNZ7ZPohEcdFjHWaVRh2AQEJDLiJdh/TFeCwN/GTGk 2fzjuOYaurQdHWD0oNdgWVeU/Dp81Sc= X-MC-Unique: DvuFZHtZPDepWhL3oQg9xA-1 X-Mimecast-MFC-AGG-ID: DvuFZHtZPDepWhL3oQg9xA From: Cornelia Huck To: eric.auger.pro@gmail.com, eric.auger@redhat.com, qemu-devel@nongnu.org, qemu-arm@nongnu.org, kvmarm@lists.linux.dev, peter.maydell@linaro.org, richard.henderson@linaro.org, alex.bennee@linaro.org, maz@kernel.org, oliver.upton@linux.dev, sebott@redhat.com, shameerali.kolothum.thodi@huawei.com, armbru@redhat.com, berrange@redhat.com, abologna@redhat.com, jdenemar@redhat.com Cc: shahuang@redhat.com, mark.rutland@arm.com, philmd@linaro.org, pbonzini@redhat.com, Cornelia Huck Subject: [PATCH RFCv2 18/20] arm/cpu: more customization for the kvm host cpu model Date: Fri, 6 Dec 2024 12:22:11 +0100 Message-ID: <20241206112213.88394-19-cohuck@redhat.com> In-Reply-To: <20241206112213.88394-1-cohuck@redhat.com> References: <20241206112213.88394-1-cohuck@redhat.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Scanned-By: MIMEDefang 3.0 on 10.30.177.12 Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=170.10.129.124; envelope-from=cohuck@redhat.com; helo=us-smtp-delivery-124.mimecast.com X-Spam_score_int: -50 X-Spam_score: -5.1 X-Spam_bar: ----- X-Spam_report: (-5.1 / 5.0 requ) BAYES_00=-1.9, DKIMWL_WL_HIGH=-2.996, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_NONE=-0.0001, RCVD_IN_MSPIKE_H2=-0.001, RCVD_IN_VALIDITY_RPBL_BLOCKED=0.001, RCVD_IN_VALIDITY_SAFE_BLOCKED=0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=unavailable autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZohoMail-DKIM: pass (identity @redhat.com) X-ZM-MESSAGEID: 1733484361801116600 Content-Type: text/plain; charset="utf-8" From: Eric Auger If the interface for writable ID registers is available, expose uint64 SYSREG properties for writable ID reg fields exposed by the host kernel. Properties are named SYSREG__ with REG and FIELD being those used in linux arch/arm64/tools/sysreg. This done by matching the writable fields retrieved from the host kernel against the generated description of sysregs. An example of invocation is: -cpu host,SYSREG_ID_AA64ISAR0_EL1_DP=3D0x0 which sets DP field of ID_AA64ISAR0_EL1 to 0. [CH: add properties to the host model instead of introducing a new "custom" model] Signed-off-by: Eric Auger Signed-off-by: Cornelia Huck --- Interaction with the existing cpu properties is still a bit unclear -- at the moment, the different configurations can overwrite each other. --- target/arm/cpu.c | 12 ++++ target/arm/cpu64.c | 150 +++++++++++++++++++++++++++++++++++++++- target/arm/trace-events | 6 ++ 3 files changed, 167 insertions(+), 1 deletion(-) diff --git a/target/arm/cpu.c b/target/arm/cpu.c index fee822eaf416..c20550cccbd2 100644 --- a/target/arm/cpu.c +++ b/target/arm/cpu.c @@ -1999,6 +1999,18 @@ static void arm_cpu_realizefn(DeviceState *dev, Erro= r **errp) return; } =20 + /* + * If we failed to retrieve the set of writable ID registers for the "= host" + * CPU model, report it here. No error if the interface for discovering + * writable ID registers is not available. + * In case we did get the set of writable ID registers, set the featur= es to + * the configured values here and perform some sanity checks. + */ + if (cpu->writable_id_regs =3D=3D WRITABLE_ID_REGS_FAILED) { + error_setg(errp, "Failed to discover writable id registers"); + return; + } + if (!cpu->gt_cntfrq_hz) { /* * 0 means "the board didn't set a value, use the default". (We al= so diff --git a/target/arm/cpu64.c b/target/arm/cpu64.c index e23df993e00e..7c75779d1eb1 100644 --- a/target/arm/cpu64.c +++ b/target/arm/cpu64.c @@ -20,6 +20,7 @@ =20 #include "qemu/osdep.h" #include "qapi/error.h" +#include "qemu/error-report.h" #include "cpu.h" #include "cpregs.h" #include "qemu/module.h" @@ -36,6 +37,7 @@ #include "cpu-features.h" #include "cpregs.h" #include "cpu-custom.h" +#include "trace.h" =20 void arm_cpu_sve_finalize(ARMCPU *cpu, Error **errp) { @@ -713,15 +715,161 @@ static void aarch64_a53_initfn(Object *obj) define_cortex_a72_a57_a53_cp_reginfo(cpu); } =20 +#ifdef CONFIG_KVM + +static ARM64SysRegField *get_field(int i, ARM64SysReg *reg) +{ + GList *l; + + for (l =3D reg->fields; l; l =3D l->next) { + ARM64SysRegField *field =3D (ARM64SysRegField *)l->data; + + if (i >=3D field->lower && i <=3D field->upper) { + return field; + } + } + return NULL; +} + +static void set_sysreg_prop(Object *obj, Visitor *v, + const char *name, void *opaque, + Error **errp) +{ + ARM64SysRegField *field =3D (ARM64SysRegField *)opaque; + ARMCPU *cpu =3D ARM_CPU(obj); + IdRegMap *idregs =3D &cpu->isar.idregs; + uint64_t old, value, mask; + int lower =3D field->lower; + int upper =3D field->upper; + int length =3D upper - lower + 1; + int index =3D field->index; + + if (!visit_type_uint64(v, name, &value, errp)) { + return; + } + + if (length < 64 && value > ((1 << length) - 1)) { + error_setg(errp, + "idreg %s set value (0x%lx) exceeds length of field (%d= )!", + name, value, length); + return; + } + + mask =3D MAKE_64BIT_MASK(lower, length); + value =3D value << lower; + old =3D idregs->regs[index]; + idregs->regs[index] =3D old & ~mask; + idregs->regs[index] |=3D value; + trace_set_sysreg_prop(name, old, mask, value, idregs->regs[index]); +} + +static void get_sysreg_prop(Object *obj, Visitor *v, + const char *name, void *opaque, + Error **errp) +{ + ARM64SysRegField *field =3D (ARM64SysRegField *)opaque; + ARMCPU *cpu =3D ARM_CPU(obj); + IdRegMap *idregs =3D &cpu->isar.idregs; + int index =3D field->index; + + error_report("%s %s", __func__, name); + visit_type_uint64(v, name, &idregs->regs[index], errp); + trace_get_sysreg_prop(name, idregs->regs[index]); +} + +/* + * decode_idreg_writemap: Generate props for writable fields + * + * @obj: CPU object + * @index: index of the sysreg + * @map: writable map for the sysreg + * @reg: description of the sysreg + */ +static int +decode_idreg_writemap(Object *obj, int index, uint64_t map, ARM64SysReg *r= eg) +{ + int i =3D ctz64(map); + int nb_sysreg_props =3D 0; + + while (map) { + ARM64SysRegField *field =3D get_field(i, reg); + int lower, upper; + uint64_t mask; + char *prop_name; + + if (!field) { + /* the field cannot be matched to any know id named field */ + warn_report("%s bit %d of %s is writable but cannot be matched= ", + __func__, i, reg->name); + warn_report("%s is cpu-sysreg-properties.c up to date?", __fun= c__); + map =3D map & ~BIT_ULL(i); + i =3D ctz64(map); + continue; + } + lower =3D field->lower; + upper =3D field->upper; + prop_name =3D g_strdup_printf("SYSREG_%s_%s", reg->name, field->na= me); + trace_decode_idreg_writemap(field->name, lower, upper, prop_name); + object_property_add(obj, prop_name, "uint64", + get_sysreg_prop, set_sysreg_prop, NULL, field); + nb_sysreg_props++; + + mask =3D MAKE_64BIT_MASK(lower, upper - lower + 1); + map =3D map & ~mask; + i =3D ctz64(map); + } + trace_nb_sysreg_props(reg->name, nb_sysreg_props); + return 0; +} + +/* analyze the writable mask and generate properties for writable fields */ +static int expose_idreg_properties(Object *obj, IdRegMap *map, + ARM64SysReg *regs) +{ + int i; + + for (i =3D 0; i < NR_ID_REGS; i++) { + uint64_t mask =3D map->regs[i]; + + if (mask) { + /* reg @i has some writable fields, decode them */ + decode_idreg_writemap(obj, i, mask, ®s[i]); + } + } + return 0; +} + +#endif + static void aarch64_host_initfn(Object *obj) { #if defined(CONFIG_KVM) ARMCPU *cpu =3D ARM_CPU(obj); - kvm_arm_set_cpu_features_from_host(cpu, false); + bool expose_id_regs =3D true; + int ret; + + cpu->writable_map =3D g_malloc(sizeof(IdRegMap)); + + /* discover via KVM_ARM_GET_REG_WRITABLE_MASKS */ + ret =3D kvm_arm_get_writable_id_regs(cpu, cpu->writable_map); + if (ret =3D=3D -ENOSYS) { + /* legacy: continue without writable id regs */ + expose_id_regs =3D false; + } else if (ret) { + /* function will have marked an error */ + return; + } + + kvm_arm_set_cpu_features_from_host(cpu, expose_id_regs); if (arm_feature(&cpu->env, ARM_FEATURE_AARCH64)) { aarch64_add_sve_properties(obj); aarch64_add_pauth_properties(obj); } + if (expose_id_regs) { + /* generate SYSREG properties according to writable masks */ + expose_idreg_properties(obj, cpu->writable_map, arm64_id_regs); + } + #elif defined(CONFIG_HVF) ARMCPU *cpu =3D ARM_CPU(obj); hvf_arm_set_cpu_features_from_host(cpu, false); diff --git a/target/arm/trace-events b/target/arm/trace-events index 668acf94ab60..1b4bd5ab1498 100644 --- a/target/arm/trace-events +++ b/target/arm/trace-events @@ -15,3 +15,9 @@ arm_gt_update_irq(int timer, int irqstate) "gt_update_irq= : timer %d irqstate %d" kvm_arm_fixup_msi_route(uint64_t iova, uint64_t gpa) "MSI iova =3D 0x%"PRI= x64" is translated into 0x%"PRIx64 get_host_cpu_idregs(const char *name, uint64_t value) "scratch vcpu gost v= alue for %s is 0x%"PRIx64 kvm_arm_writable_idregs_to_cpreg_list(const char *name, uint64_t previous,= uint64_t new) "%s overwrite default 0x%"PRIx64" with 0x%"PRIx64 + +# cpu64.c +decode_idreg_writemap(const char* name, int lower, int upper, char *prop_n= ame) "%s [%d:%d] is writable (prop %s)" +get_sysreg_prop(const char *name, uint64_t value) "%s 0x%"PRIx64 +set_sysreg_prop(const char *name, uint64_t old, uint64_t mask, uint64_t fi= eld_value, uint64_t new) "%s old reg value=3D0x%"PRIx64" mask=3D0x%"PRIx64"= new field value=3D0x%"PRIx64" new reg value=3D0x%"PRIx64 +nb_sysreg_props(const char *name, int count) "%s: %d SYSREG properties" --=20 2.47.0