Received: by 2002:a6b:fb09:0:0:0:0:0 with SMTP id h9csp3400278iog; Mon, 27 Jun 2022 15:31:04 -0700 (PDT) X-Google-Smtp-Source: AGRyM1slAiH1OOqRp+QS3ZYzjc304bTtqAuJCUo2kpmKehvxHyi9k0y/mNY34SaxKYdC0nfbpFX4 X-Received: by 2002:a17:90b:4a4c:b0:1ec:9036:8f91 with SMTP id lb12-20020a17090b4a4c00b001ec90368f91mr18140295pjb.33.1656369063582; Mon, 27 Jun 2022 15:31:03 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1656369063; cv=none; d=google.com; s=arc-20160816; b=aSR2xsY619GL7A+EXMNSZEl7giriqO87rbxErthx0TbripHKmGie8hqgusF5/9LBdm y9bopoZYJzVVNpjps5+JHFypN0Jb6S0noOzRIDRmMgwrteGN/GNqAo4tb06unq+iL84g 9wCaJQok3o7/5MbNSmxZ0LRUxM4eWI9sMBKueeRKGdXCPN5al+VI7SCD3Km5/E9k619I AptjmJSRGtjS7XU5NJL7VbI89an3dC1lLhdaUD8zdPUGR9TxzudfKczwUkOSkPJ9jEOz +evgi8S/S2vtWjUF6JJICoOXtvDqAZXTvzQZY1TWu1tJ1tjRPuzTULf9k5Ua4oeZG3HE QIpg== 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:cc:to:from :dkim-signature; bh=01Hj/MpRUEZeZ3ZaEdk358KTLv9dgc3gJFuQNv4B10w=; b=VvQ6AlXrAGkZMbXCwwoh0KD0niomykEwjr9ebC/9F4I2cGmsek7yN2/jUhsKuTv0LB u7+Q++bxsgEAlKRUHyGeLrgPV85J16F5fXEK9OYSMh7LBTrhCyia2jcufuqFmoEvWiy4 AKEipO1pAaf/84OXK/iL1tm8L8Ii8IQ8/sOBU9ZgZH3o26cRudBGeV3wN6kpfcHs51Ed aGwBacrbFEpXJl3JQ3wmmfuffAbdkUUBxhAWES/fpVvh7DiwxMPycvfb6vy5ys+Xmr+D GDZiG63HRf20nrRg4osBw4A/4euMKEVt0/3gn4pZ0zcYhFguQUXERPRxLKFmUTVESHNg GuEA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b=NAnLHUxL; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id bm28-20020a656e9c000000b0040d3151251fsi16648731pgb.807.2022.06.27.15.30.50; Mon, 27 Jun 2022 15:31:03 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b=NAnLHUxL; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S241590AbiF0V7h (ORCPT + 99 others); Mon, 27 Jun 2022 17:59:37 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:60284 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S241538AbiF0Vzk (ORCPT ); Mon, 27 Jun 2022 17:55:40 -0400 Received: from mga11.intel.com (mga11.intel.com [192.55.52.93]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 828CEF5B6; Mon, 27 Jun 2022 14:55:03 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1656366903; x=1687902903; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=Ok0044DbrsgcuNJNzGhk84qOYw5k5tS/LDbhV8oGjXY=; b=NAnLHUxLIjGqZOX+iy1Wz3s6+eSA/qkys5GzAMqRuT10FEDslMNPsUGT /P3kJL0Ds0UcelsL6ViO6AeAo9WYgzo7HvsMX/4l+LUOAFMiZfzUyvfA8 Zze0e84m8Ck90E8PY0rcCG5H/HSJHUCdM4DOjj8c94CmjTYKj4sByHYuj l0kIAyIMcVAv1xGVC1FPwE16TPf0+OrSHRIYlBmrl6CDPMs6Rm7w3FoWZ we1oqMm/rXUzdQTsN7MZYloAKJJwwHQ2j9J6syF+bXS/j0GxBVh5hEGAN +LFsioUscRXA0DDrIVy60MvwPpNgI+T09l28sc6eKceAovTydphMZ9KOX g==; X-IronPort-AV: E=McAfee;i="6400,9594,10391"; a="279116116" X-IronPort-AV: E=Sophos;i="5.92,227,1650956400"; d="scan'208";a="279116116" Received: from fmsmga004.fm.intel.com ([10.253.24.48]) by fmsmga102.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 27 Jun 2022 14:54:58 -0700 X-IronPort-AV: E=Sophos;i="5.92,227,1650956400"; d="scan'208";a="657863675" Received: from ls.sc.intel.com (HELO localhost) ([143.183.96.54]) by fmsmga004-auth.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 27 Jun 2022 14:54:58 -0700 From: isaku.yamahata@intel.com To: kvm@vger.kernel.org, linux-kernel@vger.kernel.org Cc: isaku.yamahata@intel.com, isaku.yamahata@gmail.com, Paolo Bonzini , Xiaoyao Li , Sean Christopherson , Chao Gao Subject: [PATCH v7 073/102] KVM: x86: Add a switch_db_regs flag to handle TDX's auto-switched behavior Date: Mon, 27 Jun 2022 14:54:05 -0700 Message-Id: <105e8d5126bb9a4bedb4e8668ed04e30861a568f.1656366338.git.isaku.yamahata@intel.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-7.5 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,RCVD_IN_DNSWL_HI, SPF_HELO_NONE,SPF_NONE,T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Isaku Yamahata Add a flag, KVM_DEBUGREG_AUTO_SWITCHED_GUEST, to skip saving/restoring DRs irrespective of any other flags. TDX-SEAM unconditionally saves and restores guest DRs and reset to architectural INIT state on TD exit. So, KVM needs to save host DRs before TD enter without restoring guest DRs and restore host DRs after TD exit. Opportunistically convert the KVM_DEBUGREG_* definitions to use BIT(). Reported-by: Xiaoyao Li Signed-off-by: Sean Christopherson Co-developed-by: Chao Gao Signed-off-by: Chao Gao Signed-off-by: Isaku Yamahata --- arch/x86/include/asm/kvm_host.h | 9 +++++++-- arch/x86/kvm/vmx/tdx.c | 1 + arch/x86/kvm/x86.c | 11 ++++++++--- 3 files changed, 16 insertions(+), 5 deletions(-) diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h index a1d186190287..1f5be98b7630 100644 --- a/arch/x86/include/asm/kvm_host.h +++ b/arch/x86/include/asm/kvm_host.h @@ -556,8 +556,13 @@ struct kvm_pmu { struct kvm_pmu_ops; enum { - KVM_DEBUGREG_BP_ENABLED = 1, - KVM_DEBUGREG_WONT_EXIT = 2, + KVM_DEBUGREG_BP_ENABLED = BIT(0), + KVM_DEBUGREG_WONT_EXIT = BIT(1), + /* + * Guest debug registers are saved/restored by hardware on exit from + * or enter guest. KVM needn't switch them. + */ + KVM_DEBUGREG_AUTO_SWITCH = BIT(2), }; struct kvm_mtrr_range { diff --git a/arch/x86/kvm/vmx/tdx.c b/arch/x86/kvm/vmx/tdx.c index 4db9bfe2c534..c256853efed5 100644 --- a/arch/x86/kvm/vmx/tdx.c +++ b/arch/x86/kvm/vmx/tdx.c @@ -545,6 +545,7 @@ int tdx_vcpu_create(struct kvm_vcpu *vcpu) vcpu->arch.efer = EFER_SCE | EFER_LME | EFER_LMA | EFER_NX; + vcpu->arch.switch_db_regs = KVM_DEBUGREG_AUTO_SWITCH; vcpu->arch.cr0_guest_owned_bits = -1ul; vcpu->arch.cr4_guest_owned_bits = -1ul; diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index ce0ef32c2619..39473b561e27 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -10326,7 +10326,7 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu) if (vcpu->arch.guest_fpu.xfd_err) wrmsrl(MSR_IA32_XFD_ERR, vcpu->arch.guest_fpu.xfd_err); - if (unlikely(vcpu->arch.switch_db_regs)) { + if (unlikely(vcpu->arch.switch_db_regs & ~KVM_DEBUGREG_AUTO_SWITCH)) { set_debugreg(0, 7); set_debugreg(vcpu->arch.eff_db[0], 0); set_debugreg(vcpu->arch.eff_db[1], 1); @@ -10368,6 +10368,7 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu) */ if (unlikely(vcpu->arch.switch_db_regs & KVM_DEBUGREG_WONT_EXIT)) { WARN_ON(vcpu->guest_debug & KVM_GUESTDBG_USE_HW_BP); + WARN_ON(vcpu->arch.switch_db_regs & KVM_DEBUGREG_AUTO_SWITCH); static_call(kvm_x86_sync_dirty_debug_regs)(vcpu); kvm_update_dr0123(vcpu); kvm_update_dr7(vcpu); @@ -10380,8 +10381,12 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu) * care about the messed up debug address registers. But if * we have some of them active, restore the old state. */ - if (hw_breakpoint_active()) - hw_breakpoint_restore(); + if (hw_breakpoint_active()) { + if (!(vcpu->arch.switch_db_regs & KVM_DEBUGREG_AUTO_SWITCH)) + hw_breakpoint_restore(); + else + set_debugreg(__this_cpu_read(cpu_dr7), 7); + } vcpu->arch.last_vmentry_cpu = vcpu->cpu; vcpu->arch.last_guest_tsc = kvm_read_l1_tsc(vcpu, rdtsc()); -- 2.25.1