Received: by 2002:ab2:3319:0:b0:1ef:7a0f:c32d with SMTP id i25csp942995lqc; Fri, 8 Mar 2024 17:37:20 -0800 (PST) X-Forwarded-Encrypted: i=3; AJvYcCWgHjr9shQ4BcFNodVjR6Mja01EcPYTkKhFr5/z+Pqifdu4zQc1UMJaeqmoQ+FEAfW47eKA0zkJWxlN6P9GilefksDuqeW3kR36+hhVrA== X-Google-Smtp-Source: AGHT+IEuI+FopKJRYVveVTF04y+Rjy1xovoiHnD7osuoLzh6TWI/d3Q76AHC7FhzyQrH4CyLTm/B X-Received: by 2002:a0d:d90e:0:b0:60a:427:83d9 with SMTP id b14-20020a0dd90e000000b0060a042783d9mr959273ywe.16.1709948239816; Fri, 08 Mar 2024 17:37:19 -0800 (PST) ARC-Seal: i=2; a=rsa-sha256; t=1709948239; cv=pass; d=google.com; s=arc-20160816; b=aPdQJqKdbVL0pgASGZpRWlnTQTNToImPtfk38pDfmjFQF+mwgwZqRMyibQ0US+zSCb 19lIqVww5zFo7Lc1XGx1SJMijD0nTG+Y1vzXWdwWESXHM/1Sr0bSxx+fFQHAnPi8QrGr lAtvIVCSNujKOzX4+h+45LyJzTtaeSZTCjVCg4kqyVWgKpdBcY9PvGU3JJPoz6u5Fjt6 7Z6fMN89CD0lY9yTDhns+UsTkh5sqPZ19gNgHSURO+W9la20DGBMPv0Y70gGr1y08QKz r7a0QavaPpN6yccllFJAQM2uJqlMKd51u7iFgGoQV1RkyXv+zAfGnfmRwDu7+C/I1rGq rVyQ== ARC-Message-Signature: i=2; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=cc:to:from:subject:message-id:references:mime-version :list-unsubscribe:list-subscribe:list-id:precedence:in-reply-to:date :reply-to:dkim-signature; bh=y0BhAxRzKsAvo5OwS6Sm/EpbJRorm6UaRPV9uoZ1QIo=; fh=NMXNtOsVqjlOwX2ay7/CIal8Onc3M2cfgTfmBdu1VE4=; b=KJvvuasKjifN71SDh7XrGrffB6OAmnjXc0GJqsSBNU4gvNe0gL/nf8muefArdzgWgg H67wJYb7dmgDN9VLKgNk+wJK/IdELAfrQ3eDIHxaXCMIOW+SJFoLPo9Ih1rrj1vhtbCW u03kwkwnD0CrdJ5jelCP/D2MPFQP4ByMVB29h7RO8ORrhEKZtV19FFZ5beD8Fe/t9igW W9GB/U3QXdP9QdeYpMsn3zd0RAdxsfuJQhUELBSMptXlgiMEG2NgpFSeW/crihpAAQcO abQQgvPModgqGZzVNhQzZ/htXxNq+jOxKypRSzUNcGfcWGv83lKPqGymD81ER+inaFlY vyxQ==; dara=google.com ARC-Authentication-Results: i=2; mx.google.com; dkim=pass header.i=@google.com header.s=20230601 header.b=KSayU958; arc=pass (i=1 spf=pass spfdomain=flex--seanjc.bounces.google.com dkim=pass dkdomain=google.com dmarc=pass fromdomain=google.com); spf=pass (google.com: domain of linux-kernel+bounces-97738-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45d1:ec00::1 as permitted sender) smtp.mailfrom="linux-kernel+bounces-97738-linux.lists.archive=gmail.com@vger.kernel.org"; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=google.com Return-Path: Received: from ny.mirrors.kernel.org (ny.mirrors.kernel.org. [2604:1380:45d1:ec00::1]) by mx.google.com with ESMTPS id 6-20020ac84e86000000b0042ef431349fsi784633qtp.806.2024.03.08.17.37.19 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 08 Mar 2024 17:37:19 -0800 (PST) Received-SPF: pass (google.com: domain of linux-kernel+bounces-97738-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45d1:ec00::1 as permitted sender) client-ip=2604:1380:45d1:ec00::1; Authentication-Results: mx.google.com; dkim=pass header.i=@google.com header.s=20230601 header.b=KSayU958; arc=pass (i=1 spf=pass spfdomain=flex--seanjc.bounces.google.com dkim=pass dkdomain=google.com dmarc=pass fromdomain=google.com); spf=pass (google.com: domain of linux-kernel+bounces-97738-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45d1:ec00::1 as permitted sender) smtp.mailfrom="linux-kernel+bounces-97738-linux.lists.archive=gmail.com@vger.kernel.org"; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=google.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 ny.mirrors.kernel.org (Postfix) with ESMTPS id 7D6E01C2141F for ; Sat, 9 Mar 2024 01:37:19 +0000 (UTC) Received: from localhost.localdomain (localhost.localdomain [127.0.0.1]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 49D8125630; Sat, 9 Mar 2024 01:36:49 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="KSayU958" Received: from mail-yb1-f201.google.com (mail-yb1-f201.google.com [209.85.219.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 953DA17554 for ; Sat, 9 Mar 2024 01:36:46 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.219.201 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1709948208; cv=none; b=H1oi9hdd17f4HucTXgsMdEDZfPOREfLD0Fe5opUsTmAFuF0VBUjuEjvocpyclGveqEsMNn29nyvNZm+K6Bl1f+UvCPrAC6maYAToMdtp9oQOMrf6PCUI5iGtN3o/DUuUzqqsvAI9yXlz2cFJT29CPJWJ8TlO3umDzBw8Xfgq3Vg= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1709948208; c=relaxed/simple; bh=VJikoSrQo43avUuqAwx40juOg+W7uxK2JNJYf8WFBZc=; h=Date:In-Reply-To:Mime-Version:References:Message-ID:Subject:From: To:Cc:Content-Type; b=OtoGlMAl7ME+QyHEuNGXX2C+gy/dC3bZVGPi+A2qzOMyWuKW+VGAX2qp78bhbVHfjeecLdJsBt7TG0FYt67I31N500lVkQURJL9ttUDUVlijWPl2ir36Hj6zfEvN2GoYEaEgQRIqpNoHWcJskZJEw8+3DPf+Wmu8bGNjMaz5AmA= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--seanjc.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=KSayU958; arc=none smtp.client-ip=209.85.219.201 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--seanjc.bounces.google.com Received: by mail-yb1-f201.google.com with SMTP id 3f1490d57ef6-dcc58cddb50so4408994276.0 for ; Fri, 08 Mar 2024 17:36:46 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1709948205; x=1710553005; darn=vger.kernel.org; h=cc:to:from:subject:message-id:references:mime-version:in-reply-to :date:reply-to:from:to:cc:subject:date:message-id:reply-to; bh=y0BhAxRzKsAvo5OwS6Sm/EpbJRorm6UaRPV9uoZ1QIo=; b=KSayU958IypRqhH6kxzGdePO9rJCxvJvHnnbJwOF3DXada6AHEmKUR7DUusDA9o+sM Vl/XG26p9FuhfOTRUu2lxWDdSBtxN9sknEqghv66KejDsDUO3gu2pTCJhTBz9+k7agZj T3RbtUq+GIFywlsOn2ttMMAx6GdNM/kBdtEwgDWLP2qM8/RPc5lVPm525aLSG9CRbPw+ 7iQoIOB9iykvSg+Wz5Ie7gomuvSB+SxSnZiDF7wKeLPoirEHhJ5MebajYYmqU48bezrO 3lWWi+wDK5bhJ9JOaDDZ2AN6FW2uYoI4ooY2qgxmTterp/w/RO/akHoJEGeJkvihd5Ex CKUg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1709948205; x=1710553005; h=cc:to:from:subject:message-id:references:mime-version:in-reply-to :date:reply-to:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=y0BhAxRzKsAvo5OwS6Sm/EpbJRorm6UaRPV9uoZ1QIo=; b=bjkNEn/TER+jcZVor65MPTHcc2EV5s63lAYttA9mupSyOrnR1NXWBhMERNp9zgyGz6 Qic3HvD4nmbK1bxfNVbWUASr0z9le+7MT7whbweX9bxPEhhXBCeNYJWS9bySkXEsDkx5 ragXAv6UZ+Y4cfj0EJ8dRN727hNoPefh/1JeFjBGc0r05kDVqiEexV29M762FOBP9oV2 RKLVGZXFJ4bdrTdfPzgNLNgIJp67IgEEgodrAG0hL03jXEHVc9/67P/NvCgX+CHntVCR 7aZB/5v5fbKaK452QQfnqK066ivzMK4/KIPxFiMY/RXJzQLc9kgdlEHqxQjjCQcLKNG/ iCkw== X-Forwarded-Encrypted: i=1; AJvYcCXb9VQwC1wgzQ4ngNwn0NGzx2lhw9z+KNcu5GdqfOJAbjq8PJVKY0W1g8CZO7zEhz4Os0ZPBL4VOo/BSY/2glHWM+oNPHcCrKHx1csI X-Gm-Message-State: AOJu0Yxh+jqznX2dB9b/dsB7w+NzHXExNJmVp3/m1PLbYdZCKA4OdfIe 7XHzrxuHXJV3Tu5q2t/35/NwuscSUpttOhhrOvYjtoximtKCv/p1047cVx5Gzl14+NK1me8JGdI +qA== X-Received: from zagreus.c.googlers.com ([fda3:e722:ac3:cc00:7f:e700:c0a8:5c37]) (user=seanjc job=sendgmr) by 2002:a25:aa83:0:b0:dc2:3441:897f with SMTP id t3-20020a25aa83000000b00dc23441897fmr188875ybi.6.1709948205744; Fri, 08 Mar 2024 17:36:45 -0800 (PST) Reply-To: Sean Christopherson Date: Fri, 8 Mar 2024 17:36:40 -0800 In-Reply-To: <20240309013641.1413400-1-seanjc@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20240309013641.1413400-1-seanjc@google.com> X-Mailer: git-send-email 2.44.0.278.ge034bb2e1d-goog Message-ID: <20240309013641.1413400-2-seanjc@google.com> Subject: [PATCH 1/2] KVM: x86/pmu: Set enable bits for GP counters in PERF_GLOBAL_CTRL at "RESET" From: Sean Christopherson To: Sean Christopherson , Paolo Bonzini Cc: kvm@vger.kernel.org, linux-kernel@vger.kernel.org, Babu Moger , Sandipan Das , Like Xu , Mingwei Zhang , Dapeng Mi Content-Type: text/plain; charset="UTF-8" Set the enable bits for general purpose counters in IA32_PERF_GLOBAL_CTRL when refreshing the PMU to emulate the MSR's architecturally defined post-RESET behavior. Per Intel's SDM: IA32_PERF_GLOBAL_CTRL: Sets bits n-1:0 and clears the upper bits. and Where "n" is the number of general-purpose counters available in the processor. AMD also documents this behavior for PerfMonV2 CPUs in one of AMD's many PPRs. Do not set any PERF_GLOBAL_CTRL bits if there are no general purpose counters, although a literal reading of the SDM would require the CPU to set either bits 63:0 or 31:0. The intent of the behavior is to globally enable all GP counters; honor the intent, if not the letter of the law. Leaving PERF_GLOBAL_CTRL '0' effectively breaks PMU usage in guests that haven't been updated to work with PMUs that support PERF_GLOBAL_CTRL. This bug was recently exposed when KVM added supported for AMD's PerfMonV2, i.e. when KVM started exposing a vPMU with PERF_GLOBAL_CTRL to guest software that only knew how to program v1 PMUs (that don't support PERF_GLOBAL_CTRL). Failure to emulate the post-RESET behavior results in such guests unknowingly leaving all general purpose counters globally disabled (the entire reason the post-RESET value sets the GP counter enable bits is to maintain backwards compatibility). The bug has likely gone unnoticed because PERF_GLOBAL_CTRL has been supported on Intel CPUs for as long as KVM has existed, i.e. hardly anyone is running guest software that isn't aware of PERF_GLOBAL_CTRL on Intel PMUs. And because up until v6.0, KVM _did_ emulate the behavior for Intel CPUs, although the old behavior was likely dumb luck. Because (a) that old code was also broken in its own way (the history of this code is a comedy of errors), and (b) PERF_GLOBAL_CTRL was documented as having a value of '0' post-RESET in all SDMs before March 2023. Initial vPMU support in commit f5132b01386b ("KVM: Expose a version 2 architectural PMU to a guests") *almost* got it right (again likely by dumb luck), but for some reason only set the bits if the guest PMU was advertised as v1: if (pmu->version == 1) { pmu->global_ctrl = (1 << pmu->nr_arch_gp_counters) - 1; return; } Commit f19a0c2c2e6a ("KVM: PMU emulation: GLOBAL_CTRL MSR should be enabled on reset") then tried to remedy that goof, presumably because guest PMUs were leaving PERF_GLOBAL_CTRL '0', i.e. weren't enabling counters. pmu->global_ctrl = ((1 << pmu->nr_arch_gp_counters) - 1) | (((1ull << pmu->nr_arch_fixed_counters) - 1) << X86_PMC_IDX_FIXED); pmu->global_ctrl_mask = ~pmu->global_ctrl; That was KVM's behavior up until commit c49467a45fe0 ("KVM: x86/pmu: Don't overwrite the pmu->global_ctrl when refreshing") removed *everything*. However, it did so based on the behavior defined by the SDM , which at the time stated that "Global Perf Counter Controls" is '0' at Power-Up and RESET. But then the March 2023 SDM (325462-079US), stealthily changed its "IA-32 and Intel 64 Processor States Following Power-up, Reset, or INIT" table to say: IA32_PERF_GLOBAL_CTRL: Sets bits n-1:0 and clears the upper bits. Note, kvm_pmu_refresh() can be invoked multiple times, i.e. it's not a "pure" RESET flow. But it can only be called prior to the first KVM_RUN, i.e. the guest will only ever observe the final value. Note #2, KVM has always cleared global_ctrl during refresh (see commit f5132b01386b ("KVM: Expose a version 2 architectural PMU to a guests")), i.e. there is no danger of breaking existing setups by clobbering a value set by userspace. Reported-by: Babu Moger Cc: Sandipan Das Cc: Like Xu Cc: Mingwei Zhang Cc: Dapeng Mi Cc: stable@vger.kernel.org Signed-off-by: Sean Christopherson --- arch/x86/kvm/pmu.c | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/arch/x86/kvm/pmu.c b/arch/x86/kvm/pmu.c index c397b28e3d1b..a593b03c9aed 100644 --- a/arch/x86/kvm/pmu.c +++ b/arch/x86/kvm/pmu.c @@ -775,8 +775,20 @@ void kvm_pmu_refresh(struct kvm_vcpu *vcpu) pmu->pebs_data_cfg_mask = ~0ull; bitmap_zero(pmu->all_valid_pmc_idx, X86_PMC_IDX_MAX); - if (vcpu->kvm->arch.enable_pmu) - static_call(kvm_x86_pmu_refresh)(vcpu); + if (!vcpu->kvm->arch.enable_pmu) + return; + + static_call(kvm_x86_pmu_refresh)(vcpu); + + /* + * At RESET, both Intel and AMD CPUs set all enable bits for general + * purpose counters in IA32_PERF_GLOBAL_CTRL (so that software that + * was written for v1 PMUs don't unknowingly leave GP counters disabled + * in the global controls). Emulate that behavior when refreshing the + * PMU so that userspace doesn't need to manually set PERF_GLOBAL_CTRL. + */ + if (kvm_pmu_has_perf_global_ctrl(pmu) && pmu->nr_arch_gp_counters) + pmu->global_ctrl = GENMASK_ULL(pmu->nr_arch_gp_counters - 1, 0); } void kvm_pmu_init(struct kvm_vcpu *vcpu) -- 2.44.0.278.ge034bb2e1d-goog