Received: by 2002:a05:7412:5112:b0:fa:6e18:a558 with SMTP id fm18csp170216rdb; Mon, 22 Jan 2024 16:14:10 -0800 (PST) X-Google-Smtp-Source: AGHT+IE5n6/Ou2iSgWqWNWsGlWK5CAdqIrGQzLETO0dR+cg8zVcXQq+3cbUMw3S6/9QMMePSgI9c X-Received: by 2002:a05:6a20:8410:b0:19a:7958:f451 with SMTP id c16-20020a056a20841000b0019a7958f451mr3023310pzd.78.1705968850660; Mon, 22 Jan 2024 16:14:10 -0800 (PST) ARC-Seal: i=2; a=rsa-sha256; t=1705968850; cv=pass; d=google.com; s=arc-20160816; b=oxy4CNy1BlrQWwrN/1xVR7r+luB1DzzJeUX6eP4T0SFmk+J5sCir8xWTCD+4SUbAiz ObogZebhaXw5t2zRvuWrA54F1bWi70nl84tdpuQzFe6wh3VRqTTc5Id/VOeAvh3JoXpA g1UUo/HLK3TSw+RGwwVIOT+srbj7TuSadRcig4wDSP4Wfx0A/sNb7G1Q6ZFsklY3GP5n il+C/ROeEtl5LMzOFGyFLr3Th8xDWWbXdqUqHDmKivHaTfo45qxue2cQJHgnISDX9H0F E7IKoCQGBPR0CLvE2ndO8Os7itGnRDsp0aZAfyI6ILI9ezrR31irZktd8glZStEx2zu4 fw4w== ARC-Message-Signature: i=2; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=content-transfer-encoding:mime-version:list-unsubscribe :list-subscribe:list-id:precedence:references:in-reply-to:message-id :date:subject:cc:to:from:dkim-signature; bh=uHZEKCciONaaVI4O27q2Le6JFTu7TmsXNS8HMfo+hrk=; fh=c+Gmj4GPUxwQsSF1h6kQgDYqxtAP9Q5MtAkeajGWLXo=; b=a+KiH0g4fLy7nqua+Es1kzlEjGiaovZz6BbfqCy7bdJqvzyxpMVhbFh8IHh+hMoKvR Ja8137PNtZ/EysVEnNdeqckQMqW/0pdNyefxoVFNfTDrVb37oO0+3AqYpfc9t/KI12Ep jIwk4DKvWkesfi2osNKwvKLeYlTrPF4qZaUUbjEV5bQuLnLoEDJiEVRRa2+Ok5hwKSWc cj/PeeHlhmM7PMN3wKOFpitsU2dplVPmKM1MVQF0YJ8d6IIn0Cr2YdFm3e9d4x2BE4Y2 uaqpmeJPQG+drWMDj7OSKBuWN3fLsO3gcTZd1f1zDR46KHqHnSCZSJjIG/iuW2/gf7c9 LLBw== ARC-Authentication-Results: i=2; mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b="UZ/a3HHc"; arc=pass (i=1 spf=pass spfdomain=intel.com dkim=pass dkdomain=intel.com dmarc=pass fromdomain=intel.com); spf=pass (google.com: domain of linux-kernel+bounces-34371-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45e3:2400::1 as permitted sender) smtp.mailfrom="linux-kernel+bounces-34371-linux.lists.archive=gmail.com@vger.kernel.org"; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Return-Path: Received: from sv.mirrors.kernel.org (sv.mirrors.kernel.org. [2604:1380:45e3:2400::1]) by mx.google.com with ESMTPS id co1-20020a17090afe8100b0028cedacbccdsi8746171pjb.53.2024.01.22.16.14.10 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 22 Jan 2024 16:14:10 -0800 (PST) Received-SPF: pass (google.com: domain of linux-kernel+bounces-34371-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45e3:2400::1 as permitted sender) client-ip=2604:1380:45e3:2400::1; Authentication-Results: mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b="UZ/a3HHc"; arc=pass (i=1 spf=pass spfdomain=intel.com dkim=pass dkdomain=intel.com dmarc=pass fromdomain=intel.com); spf=pass (google.com: domain of linux-kernel+bounces-34371-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45e3:2400::1 as permitted sender) smtp.mailfrom="linux-kernel+bounces-34371-linux.lists.archive=gmail.com@vger.kernel.org"; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Received: from smtp.subspace.kernel.org (wormhole.subspace.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by sv.mirrors.kernel.org (Postfix) with ESMTPS id 4DC9B28D270 for ; Tue, 23 Jan 2024 00:05:14 +0000 (UTC) Received: from localhost.localdomain (localhost.localdomain [127.0.0.1]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 6816263411; Mon, 22 Jan 2024 23:55:49 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=intel.com header.i=@intel.com header.b="UZ/a3HHc" Received: from mgamail.intel.com (mgamail.intel.com [192.55.52.120]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 2F93261679; Mon, 22 Jan 2024 23:55:46 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=192.55.52.120 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1705967748; cv=none; b=lSMlArgecmfwKGB9M2Ps0TJ0Us4gAy7DjDYgjSMHTHYzuYgyv8iRoMSY7vk4AXZANcR7fHtbfXVs9PijolKGBw/B7oIe4TY9iikEVTsG5EmYjpQkVLU4Z2qhIaWrarjNPKM/BjvdC1DfZlst93zl7oeAAsm3tCq1zIoq7NEzTTM= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1705967748; c=relaxed/simple; bh=aGja4z9BaMjDAnHbc9vPjPQEkdLGDoUAUn3WaEn/Hx4=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=kZ9G/3UbVy7O51ME2BPxYJIVT+ToPf7glS7R9krrqNnSAzWgBxz4tBfSg6rmC7PlLzEolHOa3zE6rA2X7VpdHpKRKLCEdu7RxpUBVFhhvxGYxwzFTobORnATzfOZq5gC+pAFg8byXNo4P0xn9WoYSfMYZ2jRblm9ndkJ64h9wA8= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=intel.com; spf=pass smtp.mailfrom=intel.com; dkim=pass (2048-bit key) header.d=intel.com header.i=@intel.com header.b=UZ/a3HHc; arc=none smtp.client-ip=192.55.52.120 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=intel.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=intel.com DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1705967746; x=1737503746; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=aGja4z9BaMjDAnHbc9vPjPQEkdLGDoUAUn3WaEn/Hx4=; b=UZ/a3HHcFErpZek5s0FE134YwvciKR3PwrpnZw99w8iYLD6kpvjYenry diBsTTf8nmnsQTpuwUrPI30wHZTB3qcTBgJI7NHlDSFhw5o16xl9hez/0 H2KHsTxryx4mBI2B4ojchY2K+WhRxXs/p1pfVV5mIj9pbeBuHOjHTgCn1 1ziXmhpx+/eI2rtiitsjc+3jwI2Ir/tXPiOIcB16kMsh1vZf/qcM19fpQ diJKtA5Ox5pmoHd2SliNO8VnvcvVZESgnm1wXslqsLuRaA6n2uyQF/rQe 9O0F9yJEMXA8Q9yWkQ1kSWpEPLenPbUJmBbAQ1QzFqBfeQ7MtGrzGv8h6 A==; X-IronPort-AV: E=McAfee;i="6600,9927,10961"; a="400217770" X-IronPort-AV: E=Sophos;i="6.05,212,1701158400"; d="scan'208";a="400217770" Received: from fmviesa001.fm.intel.com ([10.60.135.141]) by fmsmga104.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 22 Jan 2024 15:55:42 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="6.05,212,1701158400"; d="scan'208";a="27817910" Received: from ls.sc.intel.com (HELO localhost) ([172.25.112.31]) by smtpauth.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 22 Jan 2024 15:55:42 -0800 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 , erdemaktas@google.com, Sean Christopherson , Sagi Shahar , Kai Huang , chen.bo@intel.com, hang.yuan@intel.com, tina.zhang@intel.com, Xiaoyao Li , Sean Christopherson , Chao Gao Subject: [PATCH v18 077/121] KVM: x86: Add a switch_db_regs flag to handle TDX's auto-switched behavior Date: Mon, 22 Jan 2024 15:53:53 -0800 Message-Id: <6ae14d4e3a2f248879dcfc2990816f6341458c40.1705965635.git.isaku.yamahata@intel.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: References: Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit 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 | 10 ++++++++-- arch/x86/kvm/vmx/tdx.c | 1 + arch/x86/kvm/x86.c | 11 ++++++++--- 3 files changed, 17 insertions(+), 5 deletions(-) diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h index 5cb25e1f83ce..a7782a6f995a 100644 --- a/arch/x86/include/asm/kvm_host.h +++ b/arch/x86/include/asm/kvm_host.h @@ -626,8 +626,14 @@ 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 (DR0-3 and DR6) are saved/restored by hardware + * on exit from or enter to guest. KVM needn't switch them. Because DR7 + * is cleared on exit from guest, DR7 need to be saved/restored. + */ + 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 58583f0ab131..db01162de136 100644 --- a/arch/x86/kvm/vmx/tdx.c +++ b/arch/x86/kvm/vmx/tdx.c @@ -636,6 +636,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 f14e3e888842..e252372bb633 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -10973,7 +10973,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); @@ -11019,6 +11019,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); @@ -11031,8 +11032,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