* [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally
@ 2025-04-15 10:41 Dapeng Mi
2025-04-15 10:41 ` [PATCH 2/2] perf/x86/intel: Allow to update user space GPRs from PEBS records Dapeng Mi
` (2 more replies)
0 siblings, 3 replies; 5+ messages in thread
From: Dapeng Mi @ 2025-04-15 10:41 UTC (permalink / raw)
To: Peter Zijlstra, Ingo Molnar, Arnaldo Carvalho de Melo,
Namhyung Kim, Ian Rogers, Adrian Hunter, Alexander Shishkin,
Kan Liang, Andi Kleen, Eranian Stephane
Cc: linux-kernel, linux-perf-users, Dapeng Mi, Dapeng Mi
The below code would always unconditionally clear other status bits like
perf metrics overflow bit once PEBS buffer overflows.
status &= intel_ctrl | GLOBAL_STATUS_TRACE_TOPAPMI;
This is incorrect. Perf metrics overflow bit should be cleared only when
fixed counter 3 in PEBS counter group. Otherwise perf metrics overflow
could be missed to handle.
Closes: https://lore.kernel.org/all/20250225110012.GK31462@noisy.programming.kicks-ass.net/
Fixes: 7b2c05a15d29 ("perf/x86/intel: Generic support for hardware TopDown metrics")
Signed-off-by: Dapeng Mi <dapeng1.mi@linux.intel.com>
---
arch/x86/events/intel/core.c | 13 +++++++++++--
1 file changed, 11 insertions(+), 2 deletions(-)
diff --git a/arch/x86/events/intel/core.c b/arch/x86/events/intel/core.c
index 0ceaa1b07019..c6f69ce3b2b3 100644
--- a/arch/x86/events/intel/core.c
+++ b/arch/x86/events/intel/core.c
@@ -3140,7 +3140,6 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
int bit;
int handled = 0;
- u64 intel_ctrl = hybrid(cpuc->pmu, intel_ctrl);
inc_irq_stat(apic_perf_irqs);
@@ -3184,7 +3183,6 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
handled++;
x86_pmu_handle_guest_pebs(regs, &data);
static_call(x86_pmu_drain_pebs)(regs, &data);
- status &= intel_ctrl | GLOBAL_STATUS_TRACE_TOPAPMI;
/*
* PMI throttle may be triggered, which stops the PEBS event.
@@ -3195,6 +3193,15 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
*/
if (pebs_enabled != cpuc->pebs_enabled)
wrmsrl(MSR_IA32_PEBS_ENABLE, cpuc->pebs_enabled);
+
+ /*
+ * Above PEBS handler (PEBS counters snapshotting) has updated fixed
+ * counter 3 and perf metrics counts if they are in counter group,
+ * unnecessary to update again.
+ */
+ if (cpuc->events[INTEL_PMC_IDX_FIXED_SLOTS] &&
+ is_pebs_counter_event_group(cpuc->events[INTEL_PMC_IDX_FIXED_SLOTS]))
+ status &= ~GLOBAL_STATUS_PERF_METRICS_OVF_BIT;
}
/*
@@ -3214,6 +3221,8 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
static_call(intel_pmu_update_topdown_event)(NULL, NULL);
}
+ status &= hybrid(cpuc->pmu, intel_ctrl);
+
/*
* Checkpointed counters can lead to 'spurious' PMIs because the
* rollback caused by the PMI will have cleared the overflow status
base-commit: 5c3627b6f0595f1ec27e6f5df903bd072e9b9136
--
2.40.1
^ permalink raw reply [flat|nested] 5+ messages in thread
* [PATCH 2/2] perf/x86/intel: Allow to update user space GPRs from PEBS records
2025-04-15 10:41 [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Dapeng Mi
@ 2025-04-15 10:41 ` Dapeng Mi
2025-04-17 13:01 ` [tip: perf/core] " tip-bot2 for Dapeng Mi
2025-04-15 18:47 ` [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Liang, Kan
2025-04-17 13:01 ` [tip: perf/core] " tip-bot2 for Dapeng Mi
2 siblings, 1 reply; 5+ messages in thread
From: Dapeng Mi @ 2025-04-15 10:41 UTC (permalink / raw)
To: Peter Zijlstra, Ingo Molnar, Arnaldo Carvalho de Melo,
Namhyung Kim, Ian Rogers, Adrian Hunter, Alexander Shishkin,
Kan Liang, Andi Kleen, Eranian Stephane
Cc: linux-kernel, linux-perf-users, Dapeng Mi, Dapeng Mi
Currently when user samples user space GPRs (--user-regs option) with
PEBS, the user space GPRs actually always comes from software PMI
instead of from PEBS hardware. This leads to the sampled GPRs may be
inaccurate for single PEBS record case because of the skid between
counter overflow and GPRs sampling on PMI.
For the large PEBS case, the thing is even worse. If user sets
exclude_kernel attribute, large PEBS would be used to sample user space
GPRs, but since PEBS GPRs group is not really enabled, it leads to all
samples in the large PEBS record shares a same piece of user space GPRs,
like below command shows.
perf record -e branches:pu --user-regs=ip,ax -c 100000 ./foo
perf report -D | grep "AX"
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
So enable GPRs group for user space GPRs sampling and prioritize reading
GPRs from PEBS. If the PEBS sampled GPRs is not user space GPRs (single
PEBS record case), perf_sample_regs_user() modifies them to user space
GPRs.
Fixes: c22497f5838c ("perf/x86/intel: Support adaptive PEBS v4")
Signed-off-by: Dapeng Mi <dapeng1.mi@linux.intel.com>
---
arch/x86/events/intel/ds.c | 8 +++++---
1 file changed, 5 insertions(+), 3 deletions(-)
diff --git a/arch/x86/events/intel/ds.c b/arch/x86/events/intel/ds.c
index 486881fe162e..fcf9c5b26cab 100644
--- a/arch/x86/events/intel/ds.c
+++ b/arch/x86/events/intel/ds.c
@@ -1398,8 +1398,10 @@ static u64 pebs_update_adaptive_cfg(struct perf_event *event)
* + precise_ip < 2 for the non event IP
* + For RTM TSX weight we need GPRs for the abort code.
*/
- gprs = (sample_type & PERF_SAMPLE_REGS_INTR) &&
- (attr->sample_regs_intr & PEBS_GP_REGS);
+ gprs = ((sample_type & PERF_SAMPLE_REGS_INTR) &&
+ (attr->sample_regs_intr & PEBS_GP_REGS)) ||
+ ((sample_type & PERF_SAMPLE_REGS_USER) &&
+ (attr->sample_regs_user & PEBS_GP_REGS));
tsx_weight = (sample_type & PERF_SAMPLE_WEIGHT_TYPE) &&
((attr->config & INTEL_ARCH_EVENT_MASK) ==
@@ -2122,7 +2124,7 @@ static void setup_pebs_adaptive_sample_data(struct perf_event *event,
regs->flags &= ~PERF_EFLAGS_EXACT;
}
- if (sample_type & PERF_SAMPLE_REGS_INTR)
+ if (sample_type & (PERF_SAMPLE_REGS_INTR | PERF_SAMPLE_REGS_USER))
adaptive_pebs_save_regs(regs, gprs);
}
--
2.40.1
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally
2025-04-15 10:41 [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Dapeng Mi
2025-04-15 10:41 ` [PATCH 2/2] perf/x86/intel: Allow to update user space GPRs from PEBS records Dapeng Mi
@ 2025-04-15 18:47 ` Liang, Kan
2025-04-17 13:01 ` [tip: perf/core] " tip-bot2 for Dapeng Mi
2 siblings, 0 replies; 5+ messages in thread
From: Liang, Kan @ 2025-04-15 18:47 UTC (permalink / raw)
To: Dapeng Mi, Peter Zijlstra, Ingo Molnar, Arnaldo Carvalho de Melo,
Namhyung Kim, Ian Rogers, Adrian Hunter, Alexander Shishkin,
Andi Kleen, Eranian Stephane
Cc: linux-kernel, linux-perf-users, Dapeng Mi
On 2025-04-15 6:41 a.m., Dapeng Mi wrote:
> The below code would always unconditionally clear other status bits like
> perf metrics overflow bit once PEBS buffer overflows.
>
> status &= intel_ctrl | GLOBAL_STATUS_TRACE_TOPAPMI;
>
> This is incorrect. Perf metrics overflow bit should be cleared only when
> fixed counter 3 in PEBS counter group. Otherwise perf metrics overflow
> could be missed to handle.
>
> Closes: https://lore.kernel.org/all/20250225110012.GK31462@noisy.programming.kicks-ass.net/
> Fixes: 7b2c05a15d29 ("perf/x86/intel: Generic support for hardware TopDown metrics")
> Signed-off-by: Dapeng Mi <dapeng1.mi@linux.intel.com>
For the two patches,
Reviewed-by: Kan Liang <kan.liang@linux.intel.com>
Thanks,
Kan
> ---
> arch/x86/events/intel/core.c | 13 +++++++++++--
> 1 file changed, 11 insertions(+), 2 deletions(-)
>
> diff --git a/arch/x86/events/intel/core.c b/arch/x86/events/intel/core.c
> index 0ceaa1b07019..c6f69ce3b2b3 100644
> --- a/arch/x86/events/intel/core.c
> +++ b/arch/x86/events/intel/core.c
> @@ -3140,7 +3140,6 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
> struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
> int bit;
> int handled = 0;
> - u64 intel_ctrl = hybrid(cpuc->pmu, intel_ctrl);
>
> inc_irq_stat(apic_perf_irqs);
>
> @@ -3184,7 +3183,6 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
> handled++;
> x86_pmu_handle_guest_pebs(regs, &data);
> static_call(x86_pmu_drain_pebs)(regs, &data);
> - status &= intel_ctrl | GLOBAL_STATUS_TRACE_TOPAPMI;
>
> /*
> * PMI throttle may be triggered, which stops the PEBS event.
> @@ -3195,6 +3193,15 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
> */
> if (pebs_enabled != cpuc->pebs_enabled)
> wrmsrl(MSR_IA32_PEBS_ENABLE, cpuc->pebs_enabled);
> +
> + /*
> + * Above PEBS handler (PEBS counters snapshotting) has updated fixed
> + * counter 3 and perf metrics counts if they are in counter group,
> + * unnecessary to update again.
> + */
> + if (cpuc->events[INTEL_PMC_IDX_FIXED_SLOTS] &&
> + is_pebs_counter_event_group(cpuc->events[INTEL_PMC_IDX_FIXED_SLOTS]))
> + status &= ~GLOBAL_STATUS_PERF_METRICS_OVF_BIT;
> }
>
> /*
> @@ -3214,6 +3221,8 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
> static_call(intel_pmu_update_topdown_event)(NULL, NULL);
> }
>
> + status &= hybrid(cpuc->pmu, intel_ctrl);
> +
> /*
> * Checkpointed counters can lead to 'spurious' PMIs because the
> * rollback caused by the PMI will have cleared the overflow status
>
> base-commit: 5c3627b6f0595f1ec27e6f5df903bd072e9b9136
^ permalink raw reply [flat|nested] 5+ messages in thread
* [tip: perf/core] perf/x86/intel: Allow to update user space GPRs from PEBS records
2025-04-15 10:41 ` [PATCH 2/2] perf/x86/intel: Allow to update user space GPRs from PEBS records Dapeng Mi
@ 2025-04-17 13:01 ` tip-bot2 for Dapeng Mi
0 siblings, 0 replies; 5+ messages in thread
From: tip-bot2 for Dapeng Mi @ 2025-04-17 13:01 UTC (permalink / raw)
To: linux-tip-commits
Cc: Dapeng Mi, Peter Zijlstra (Intel),
Ingo Molnar, stable, x86, linux-kernel
The following commit has been merged into the perf/core branch of tip:
Commit-ID: 71dcc11c2cd9e434c34a63154ecadca21c135ddd
Gitweb: https://git.kernel.org/tip/71dcc11c2cd9e434c34a63154ecadca21c135ddd
Author: Dapeng Mi <dapeng1.mi@linux.intel.com>
AuthorDate: Tue, 15 Apr 2025 10:41:35
Committer: Ingo Molnar <mingo@kernel.org>
CommitterDate: Thu, 17 Apr 2025 14:19:38 +02:00
perf/x86/intel: Allow to update user space GPRs from PEBS records
Currently when a user samples user space GPRs (--user-regs option) with
PEBS, the user space GPRs actually always come from software PMI
instead of from PEBS hardware. This leads to the sampled GPRs to
possibly be inaccurate for single PEBS record case because of the
skid between counter overflow and GPRs sampling on PMI.
For the large PEBS case, it is even worse. If user sets the
exclude_kernel attribute, large PEBS would be used to sample user space
GPRs, but since PEBS GPRs group is not really enabled, it leads to all
samples in the large PEBS record to share the same piece of user space
GPRs, like this reproducer shows:
$ perf record -e branches:pu --user-regs=ip,ax -c 100000 ./foo
$ perf report -D | grep "AX"
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
.... AX 0x000000003a0d4ead
So enable GPRs group for user space GPRs sampling and prioritize reading
GPRs from PEBS. If the PEBS sampled GPRs is not user space GPRs (single
PEBS record case), perf_sample_regs_user() modifies them to user space
GPRs.
[ mingo: Clarified the changelog. ]
Fixes: c22497f5838c ("perf/x86/intel: Support adaptive PEBS v4")
Signed-off-by: Dapeng Mi <dapeng1.mi@linux.intel.com>
Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org>
Signed-off-by: Ingo Molnar <mingo@kernel.org>
Cc: stable@vger.kernel.org
Link: https://lore.kernel.org/r/20250415104135.318169-2-dapeng1.mi@linux.intel.com
---
arch/x86/events/intel/ds.c | 8 +++++---
1 file changed, 5 insertions(+), 3 deletions(-)
diff --git a/arch/x86/events/intel/ds.c b/arch/x86/events/intel/ds.c
index 1f7e1a6..18c3ab5 100644
--- a/arch/x86/events/intel/ds.c
+++ b/arch/x86/events/intel/ds.c
@@ -1399,8 +1399,10 @@ static u64 pebs_update_adaptive_cfg(struct perf_event *event)
* + precise_ip < 2 for the non event IP
* + For RTM TSX weight we need GPRs for the abort code.
*/
- gprs = (sample_type & PERF_SAMPLE_REGS_INTR) &&
- (attr->sample_regs_intr & PEBS_GP_REGS);
+ gprs = ((sample_type & PERF_SAMPLE_REGS_INTR) &&
+ (attr->sample_regs_intr & PEBS_GP_REGS)) ||
+ ((sample_type & PERF_SAMPLE_REGS_USER) &&
+ (attr->sample_regs_user & PEBS_GP_REGS));
tsx_weight = (sample_type & PERF_SAMPLE_WEIGHT_TYPE) &&
((attr->config & INTEL_ARCH_EVENT_MASK) ==
@@ -2123,7 +2125,7 @@ static void setup_pebs_adaptive_sample_data(struct perf_event *event,
regs->flags &= ~PERF_EFLAGS_EXACT;
}
- if (sample_type & PERF_SAMPLE_REGS_INTR)
+ if (sample_type & (PERF_SAMPLE_REGS_INTR | PERF_SAMPLE_REGS_USER))
adaptive_pebs_save_regs(regs, gprs);
}
^ permalink raw reply [flat|nested] 5+ messages in thread
* [tip: perf/core] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally
2025-04-15 10:41 [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Dapeng Mi
2025-04-15 10:41 ` [PATCH 2/2] perf/x86/intel: Allow to update user space GPRs from PEBS records Dapeng Mi
2025-04-15 18:47 ` [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Liang, Kan
@ 2025-04-17 13:01 ` tip-bot2 for Dapeng Mi
2 siblings, 0 replies; 5+ messages in thread
From: tip-bot2 for Dapeng Mi @ 2025-04-17 13:01 UTC (permalink / raw)
To: linux-tip-commits
Cc: Dapeng Mi, Peter Zijlstra (Intel),
Ingo Molnar, Kan Liang, stable, x86, linux-kernel
The following commit has been merged into the perf/core branch of tip:
Commit-ID: a5f5e1238f4ff919816f69e77d2537a48911767b
Gitweb: https://git.kernel.org/tip/a5f5e1238f4ff919816f69e77d2537a48911767b
Author: Dapeng Mi <dapeng1.mi@linux.intel.com>
AuthorDate: Tue, 15 Apr 2025 10:41:34
Committer: Ingo Molnar <mingo@kernel.org>
CommitterDate: Thu, 17 Apr 2025 14:19:07 +02:00
perf/x86/intel: Don't clear perf metrics overflow bit unconditionally
The below code would always unconditionally clear other status bits like
perf metrics overflow bit once PEBS buffer overflows:
status &= intel_ctrl | GLOBAL_STATUS_TRACE_TOPAPMI;
This is incorrect. Perf metrics overflow bit should be cleared only when
fixed counter 3 in PEBS counter group. Otherwise perf metrics overflow
could be missed to handle.
Closes: https://lore.kernel.org/all/20250225110012.GK31462@noisy.programming.kicks-ass.net/
Fixes: 7b2c05a15d29 ("perf/x86/intel: Generic support for hardware TopDown metrics")
Signed-off-by: Dapeng Mi <dapeng1.mi@linux.intel.com>
Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org>
Signed-off-by: Ingo Molnar <mingo@kernel.org>
Reviewed-by: Kan Liang <kan.liang@linux.intel.com>
Cc: stable@vger.kernel.org
Link: https://lore.kernel.org/r/20250415104135.318169-1-dapeng1.mi@linux.intel.com
---
arch/x86/events/intel/core.c | 13 +++++++++++--
1 file changed, 11 insertions(+), 2 deletions(-)
diff --git a/arch/x86/events/intel/core.c b/arch/x86/events/intel/core.c
index 09d2d66..2b70a3a 100644
--- a/arch/x86/events/intel/core.c
+++ b/arch/x86/events/intel/core.c
@@ -3049,7 +3049,6 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
int bit;
int handled = 0;
- u64 intel_ctrl = hybrid(cpuc->pmu, intel_ctrl);
inc_irq_stat(apic_perf_irqs);
@@ -3093,7 +3092,6 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
handled++;
x86_pmu_handle_guest_pebs(regs, &data);
static_call(x86_pmu_drain_pebs)(regs, &data);
- status &= intel_ctrl | GLOBAL_STATUS_TRACE_TOPAPMI;
/*
* PMI throttle may be triggered, which stops the PEBS event.
@@ -3104,6 +3102,15 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
*/
if (pebs_enabled != cpuc->pebs_enabled)
wrmsrl(MSR_IA32_PEBS_ENABLE, cpuc->pebs_enabled);
+
+ /*
+ * Above PEBS handler (PEBS counters snapshotting) has updated fixed
+ * counter 3 and perf metrics counts if they are in counter group,
+ * unnecessary to update again.
+ */
+ if (cpuc->events[INTEL_PMC_IDX_FIXED_SLOTS] &&
+ is_pebs_counter_event_group(cpuc->events[INTEL_PMC_IDX_FIXED_SLOTS]))
+ status &= ~GLOBAL_STATUS_PERF_METRICS_OVF_BIT;
}
/*
@@ -3123,6 +3130,8 @@ static int handle_pmi_common(struct pt_regs *regs, u64 status)
static_call(intel_pmu_update_topdown_event)(NULL, NULL);
}
+ status &= hybrid(cpuc->pmu, intel_ctrl);
+
/*
* Checkpointed counters can lead to 'spurious' PMIs because the
* rollback caused by the PMI will have cleared the overflow status
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2025-04-17 13:01 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2025-04-15 10:41 [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Dapeng Mi
2025-04-15 10:41 ` [PATCH 2/2] perf/x86/intel: Allow to update user space GPRs from PEBS records Dapeng Mi
2025-04-17 13:01 ` [tip: perf/core] " tip-bot2 for Dapeng Mi
2025-04-15 18:47 ` [PATCH 1/2] perf/x86/intel: Don't clear perf metrics overflow bit unconditionally Liang, Kan
2025-04-17 13:01 ` [tip: perf/core] " tip-bot2 for Dapeng Mi
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®