Received: by 2002:a05:6a10:1d13:0:0:0:0 with SMTP id pp19csp722870pxb; Wed, 25 Aug 2021 13:31:30 -0700 (PDT) X-Google-Smtp-Source: ABdhPJy9icDmQmrXNSkVw3HXmjcmn2jIOTso6xFKIJlDHK8Pto3YBuhHLfk+0as17mDRJy34dIu+ X-Received: by 2002:a05:6402:2554:: with SMTP id l20mr401928edb.252.1629923490181; Wed, 25 Aug 2021 13:31:30 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1629923490; cv=none; d=google.com; s=arc-20160816; b=W5kKxXjkIXmuekbd3402b89YUnUsF5oyq3BCy3GkhWyBD/TrauG+mTyYzPgi4Ysb7z zDhjz9RnfMe+3e9Emlo0pbf3qO5XwMWW+offdVP6e9jCnp02b0R7cAWPMjsKLIY3rKri lYjPzDWK5xu+hZ0SDKjihFXsiVYa4HY3ogaTVDGj6V9anlC5U8XQZiHBq3yOB1BAiYJI OWq85hD4fxT7Z4UxGILqGrJD5PMyXJggXUkTKXAvfRvwBm+UIpffYHSvbvIWUNYSulFp 8IjfZTPAxM63LnPr098P8DGn25lPbQgFVtMPVob17O5A5BFs7kP/U48EnkmK0FhRa55P gE6w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :references:in-reply-to:message-id:date:subject:to:from; bh=HpCpUIn/5J9QYtIT8in4DY3Ui/7bEi1nXpnmIuBtI4Y=; b=Lrcof7tSZTEp5jIJErgBJ2TULIzTeqbvaS7rWZIj33xFj2VqhJXe9R8rB6E1Z/ig+7 XXXXVql+UO//uVPYMarM2RG/9GJD57Ugmi5spGUAOM/FbQST/mtuW3dNUSLfdURb95C2 KK/95beMJHF7+HJk6G+nGeMvUMw04HDBkjEE4emWUdOYqTQm3Qn7ocFYD+NpmuiyogYe yDwd2rxPmHrOCSmiEcOY1hLwQDfXUNR7oPivB7rII8J5C2/+1i16wHR9cYgEB76LEQ9m iGG/gyMgwv07ZLSROMEX5d2tQWxlotSykH2gP4s4W6dtu/dws2YwLIbq11jyTnFRQbmX pR4g== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=arm.com Return-Path: Received: from vger.kernel.org (vger.kernel.org. [23.128.96.18]) by mx.google.com with ESMTP id rh9si995288ejb.513.2021.08.25.13.31.06; Wed, 25 Aug 2021 13:31:30 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) client-ip=23.128.96.18; Authentication-Results: mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=arm.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S241092AbhHYQTL (ORCPT + 99 others); Wed, 25 Aug 2021 12:19:11 -0400 Received: from foss.arm.com ([217.140.110.172]:54878 "EHLO foss.arm.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S241038AbhHYQSk (ORCPT ); Wed, 25 Aug 2021 12:18:40 -0400 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 6EF94142F; Wed, 25 Aug 2021 09:17:54 -0700 (PDT) Received: from monolith.cable.virginm.net (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 20EE23F66F; Wed, 25 Aug 2021 09:17:52 -0700 (PDT) From: Alexandru Elisei To: maz@kernel.org, james.morse@arm.com, suzuki.poulose@arm.com, linux-arm-kernel@lists.infradead.org, kvmarm@lists.cs.columbia.edu, will@kernel.org, linux-kernel@vger.kernel.org Subject: [RFC PATCH v4 26/39] KVM: arm64: VHE: Change MDCR_EL2 at world switch if VCPU has SPE Date: Wed, 25 Aug 2021 17:18:02 +0100 Message-Id: <20210825161815.266051-27-alexandru.elisei@arm.com> X-Mailer: git-send-email 2.33.0 In-Reply-To: <20210825161815.266051-1-alexandru.elisei@arm.com> References: <20210825161815.266051-1-alexandru.elisei@arm.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org When a VCPU has the SPE feature, MDCR_EL2 sets the buffer owning regime to EL1&0. Write the guest's MDCR_EL2 value as late as possible and restore the host's value as soon as possible at each world switch to make the profiling blackout window as small as possible for the host. Signed-off-by: Alexandru Elisei --- arch/arm64/include/asm/kvm_hyp.h | 2 +- arch/arm64/kvm/debug.c | 14 +++++++++++-- arch/arm64/kvm/hyp/vhe/switch.c | 33 +++++++++++++++++++++++------- arch/arm64/kvm/hyp/vhe/sysreg-sr.c | 2 +- 4 files changed, 40 insertions(+), 11 deletions(-) diff --git a/arch/arm64/include/asm/kvm_hyp.h b/arch/arm64/include/asm/kvm_hyp.h index 9d60b3006efc..657d0c94cf82 100644 --- a/arch/arm64/include/asm/kvm_hyp.h +++ b/arch/arm64/include/asm/kvm_hyp.h @@ -95,7 +95,7 @@ void __sve_restore_state(void *sve_pffr, u32 *fpsr); #ifndef __KVM_NVHE_HYPERVISOR__ void activate_traps_vhe_load(struct kvm_vcpu *vcpu); -void deactivate_traps_vhe_put(void); +void deactivate_traps_vhe_put(struct kvm_vcpu *vcpu); #endif u64 __guest_enter(struct kvm_vcpu *vcpu); diff --git a/arch/arm64/kvm/debug.c b/arch/arm64/kvm/debug.c index 64e8211366b6..70712cd85f32 100644 --- a/arch/arm64/kvm/debug.c +++ b/arch/arm64/kvm/debug.c @@ -249,9 +249,19 @@ void kvm_arm_setup_debug(struct kvm_vcpu *vcpu) vcpu->arch.flags |= KVM_ARM64_DEBUG_DIRTY; /* Write mdcr_el2 changes since vcpu_load on VHE systems */ - if (has_vhe() && orig_mdcr_el2 != vcpu->arch.mdcr_el2) - write_sysreg(vcpu->arch.mdcr_el2, mdcr_el2); + if (has_vhe()) { + /* + * MDCR_EL2 can modify the SPE buffer owning regime, defer the + * write until the VCPU is run. + */ + if (kvm_vcpu_has_spe(vcpu)) + goto out; + + if (orig_mdcr_el2 != vcpu->arch.mdcr_el2) + write_sysreg(vcpu->arch.mdcr_el2, mdcr_el2); + } +out: trace_kvm_arm_set_dreg32("MDSCR_EL1", vcpu_read_sys_reg(vcpu, MDSCR_EL1)); } diff --git a/arch/arm64/kvm/hyp/vhe/switch.c b/arch/arm64/kvm/hyp/vhe/switch.c index 983ba1570d72..ec4e179d56ae 100644 --- a/arch/arm64/kvm/hyp/vhe/switch.c +++ b/arch/arm64/kvm/hyp/vhe/switch.c @@ -31,12 +31,29 @@ DEFINE_PER_CPU(struct kvm_host_data, kvm_host_data); DEFINE_PER_CPU(struct kvm_cpu_context, kvm_hyp_ctxt); DEFINE_PER_CPU(unsigned long, kvm_hyp_vector); +static void __restore_host_mdcr_el2(struct kvm_vcpu *vcpu) +{ + u64 mdcr_el2; + + mdcr_el2 = read_sysreg(mdcr_el2); + mdcr_el2 &= MDCR_EL2_HPMN_MASK | MDCR_EL2_TPMS; + write_sysreg(mdcr_el2, mdcr_el2); +} + +static void __restore_guest_mdcr_el2(struct kvm_vcpu *vcpu) +{ + write_sysreg(vcpu->arch.mdcr_el2, mdcr_el2); +} + static void __activate_traps(struct kvm_vcpu *vcpu) { u64 val; ___activate_traps(vcpu); + if (kvm_vcpu_has_spe(vcpu)) + __restore_guest_mdcr_el2(vcpu); + val = read_sysreg(cpacr_el1); val |= CPACR_EL1_TTA; val &= ~CPACR_EL1_ZEN; @@ -81,7 +98,11 @@ static void __deactivate_traps(struct kvm_vcpu *vcpu) */ asm(ALTERNATIVE("nop", "isb", ARM64_WORKAROUND_SPECULATIVE_AT)); + if (kvm_vcpu_has_spe(vcpu)) + __restore_host_mdcr_el2(vcpu); + write_sysreg(CPACR_EL1_DEFAULT, cpacr_el1); + write_sysreg(vectors, vbar_el1); } NOKPROBE_SYMBOL(__deactivate_traps); @@ -90,16 +111,14 @@ void activate_traps_vhe_load(struct kvm_vcpu *vcpu) { __activate_traps_common(vcpu); - write_sysreg(vcpu->arch.mdcr_el2, mdcr_el2); + if (!kvm_vcpu_has_spe(vcpu)) + __restore_guest_mdcr_el2(vcpu); } -void deactivate_traps_vhe_put(void) +void deactivate_traps_vhe_put(struct kvm_vcpu *vcpu) { - u64 mdcr_el2 = read_sysreg(mdcr_el2); - - mdcr_el2 &= MDCR_EL2_HPMN_MASK | MDCR_EL2_TPMS; - - write_sysreg(mdcr_el2, mdcr_el2); + if (!kvm_vcpu_has_spe(vcpu)) + __restore_host_mdcr_el2(vcpu); __deactivate_traps_common(); } diff --git a/arch/arm64/kvm/hyp/vhe/sysreg-sr.c b/arch/arm64/kvm/hyp/vhe/sysreg-sr.c index 2a0b8c88d74f..007a12dd4351 100644 --- a/arch/arm64/kvm/hyp/vhe/sysreg-sr.c +++ b/arch/arm64/kvm/hyp/vhe/sysreg-sr.c @@ -101,7 +101,7 @@ void kvm_vcpu_put_sysregs_vhe(struct kvm_vcpu *vcpu) struct kvm_cpu_context *host_ctxt; host_ctxt = &this_cpu_ptr(&kvm_host_data)->host_ctxt; - deactivate_traps_vhe_put(); + deactivate_traps_vhe_put(vcpu); __sysreg_save_el1_state(guest_ctxt); __sysreg_save_user_state(guest_ctxt); -- 2.33.0