linux/arch
Athira Rajeev 875b2bf469 powerpc/perf: Optimize clearing the pending PMI and remove WARN_ON for PMI check in power_pmu_disable
[ Upstream commit 890005a7d9 ]

commit 2c9ac51b85 ("powerpc/perf: Fix PMU callbacks to clear
pending PMI before resetting an overflown PMC") added a new
function "pmi_irq_pending" in hw_irq.h. This function is to check
if there is a PMI marked as pending in Paca (PACA_IRQ_PMI).This is
used in power_pmu_disable in a WARN_ON. The intention here is to
provide a warning if there is PMI pending, but no counter is found
overflown.

During some of the perf runs, below warning is hit:

WARNING: CPU: 36 PID: 0 at arch/powerpc/perf/core-book3s.c:1332 power_pmu_disable+0x25c/0x2c0
 Modules linked in:
 -----

 NIP [c000000000141c3c] power_pmu_disable+0x25c/0x2c0
 LR [c000000000141c8c] power_pmu_disable+0x2ac/0x2c0
 Call Trace:
 [c000000baffcfb90] [c000000000141c8c] power_pmu_disable+0x2ac/0x2c0 (unreliable)
 [c000000baffcfc10] [c0000000003e2f8c] perf_pmu_disable+0x4c/0x60
 [c000000baffcfc30] [c0000000003e3344] group_sched_out.part.124+0x44/0x100
 [c000000baffcfc80] [c0000000003e353c] __perf_event_disable+0x13c/0x240
 [c000000baffcfcd0] [c0000000003dd334] event_function+0xc4/0x140
 [c000000baffcfd20] [c0000000003d855c] remote_function+0x7c/0xa0
 [c000000baffcfd50] [c00000000026c394] flush_smp_call_function_queue+0xd4/0x300
 [c000000baffcfde0] [c000000000065b24] smp_ipi_demux_relaxed+0xa4/0x100
 [c000000baffcfe20] [c0000000000cb2b0] xive_muxed_ipi_action+0x20/0x40
 [c000000baffcfe40] [c000000000207c3c] __handle_irq_event_percpu+0x8c/0x250
 [c000000baffcfee0] [c000000000207e2c] handle_irq_event_percpu+0x2c/0xa0
 [c000000baffcff10] [c000000000210a04] handle_percpu_irq+0x84/0xc0
 [c000000baffcff40] [c000000000205f14] generic_handle_irq+0x54/0x80
 [c000000baffcff60] [c000000000015740] __do_irq+0x90/0x1d0
 [c000000baffcff90] [c000000000016990] __do_IRQ+0xc0/0x140
 [c0000009732f3940] [c000000bafceaca8] 0xc000000bafceaca8
 [c0000009732f39d0] [c000000000016b78] do_IRQ+0x168/0x1c0
 [c0000009732f3a00] [c0000000000090c8] hardware_interrupt_common_virt+0x218/0x220

This means that there is no PMC overflown among the active events
in the PMU, but there is a PMU pending in Paca. The function
"any_pmc_overflown" checks the PMCs on active events in
cpuhw->n_events. Code snippet:

<<>>
if (any_pmc_overflown(cpuhw))
 	clear_pmi_irq_pending();
 else
 	WARN_ON(pmi_irq_pending());
<<>>

Here the PMC overflown is not from active event. Example: When we do
perf record, default cycles and instructions will be running on PMC6
and PMC5 respectively. It could happen that overflowed event is currently
not active and pending PMI is for the inactive event. Debug logs from
trace_printk:

<<>>
any_pmc_overflown: idx is 5: pmc value is 0xd9a
power_pmu_disable: PMC1: 0x0, PMC2: 0x0, PMC3: 0x0, PMC4: 0x0, PMC5: 0xd9a, PMC6: 0x80002011
<<>>

Here active PMC (from idx) is PMC5 , but overflown PMC is PMC6(0x80002011).
When we handle PMI interrupt for such cases, if the PMC overflown is
from inactive event, it will be ignored. Reference commit:
commit bc09c219b2 ("powerpc/perf: Fix finding overflowed PMC in interrupt")

Patch addresses two changes:
1) Fix 1 : Removal of warning ( WARN_ON(pmi_irq_pending()); )
   We were printing warning if no PMC is found overflown among active PMU
   events, but PMI pending in PACA. But this could happen in cases where
   PMC overflown is not in active PMC. An inactive event could have caused
   the overflow. Hence the warning is not needed. To know pending PMI is
   from an inactive event, we need to loop through all PMC's which will
   cause more SPR reads via mfspr and increase in context switch. Also in
   existing function: perf_event_interrupt, already we ignore PMI's
   overflown when it is from an inactive PMC.

2) Fix 2: optimization in clearing pending PMI.
   Currently we check for any active PMC overflown before clearing PMI
   pending in Paca. This is causing additional SPR read also. From point 1,
   we know that if PMI pending in Paca from inactive cases, that is going
   to be ignored during replay. Hence if there is pending PMI in Paca, just
   clear it irrespective of PMC overflown or not.

In summary, remove the any_pmc_overflown check entirely in
power_pmu_disable. ie If there is a pending PMI in Paca, clear it, since
we are in pmu_disable. There could be cases where PMI is pending because
of inactive PMC ( which later when replayed also will get ignored ), so
WARN_ON could give false warning. Hence removing it.

Fixes: 2c9ac51b85 ("powerpc/perf: Fix PMU callbacks to clear pending PMI before resetting an overflown PMC")
Signed-off-by: Athira Rajeev <atrajeev@linux.vnet.ibm.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
Link: https://lore.kernel.org/r/20220522142256.24699-1-atrajeev@linux.vnet.ibm.com
Signed-off-by: Sasha Levin <sashal@kernel.org>
2022-08-21 15:16:06 +02:00
..
alpha tty: the rest, stop using tty_schedule_flip() 2022-07-29 17:19:28 +02:00
arc ARC: entry: fix syscall_trace_exit argument 2022-04-27 13:53:55 +02:00
arm ARM: dts: qcom: pm8841: add required thermal-sensor-cells 2022-08-21 15:15:35 +02:00
arm64 KVM: arm64: Don't return from void function 2022-08-21 15:15:57 +02:00
c6x arch-cleanup-2020-10-22 2020-10-23 10:06:38 -07:00
csky csky: patch_text: Fixup last cpu should be master 2022-06-09 10:21:26 +02:00
h8300 h8300: fix PREEMPTION build, TI_PRE_COUNT undefined 2021-02-17 11:02:28 +01:00
hexagon hexagon: select ARCH_WANT_LD_ORPHAN_WARN 2022-08-21 15:15:33 +02:00
ia64 ia64, processor: fix -Wincompatible-pointer-types in ia64_get_irr() 2022-08-21 15:15:25 +02:00
m68k Revert "m68knommu: only set CONFIG_ISA_DMA_API for ColdFire sub-arch" 2022-07-29 17:19:09 +02:00
microblaze uaccess: fix nios2 and microblaze get_user_8() 2022-04-08 14:40:08 +02:00
mips MIPS: cpuinfo: Fix a warning for CONFIG_CPUMASK_OFFSTACK 2022-08-21 15:15:26 +02:00
nds32 nds32: fix access_ok() checks in get/put_user 2022-03-28 09:57:10 +02:00
nios2 nios2: use fallback for random_get_entropy() instead of zero 2022-05-30 09:33:41 +02:00
openrisc openrisc: start CPU timer early in boot 2022-06-09 10:20:55 +02:00
parisc parisc: io_pgetevents_time64() needs compat syscall in 32-bit compat mode 2022-08-21 15:15:23 +02:00
powerpc powerpc/perf: Optimize clearing the pending PMI and remove WARN_ON for PMI check in power_pmu_disable 2022-08-21 15:16:06 +02:00
riscv riscv: set default pm_power_off to NULL 2022-08-21 15:15:21 +02:00
s390 KVM: s390: pv: leak the topmost page table when destroy fails 2022-08-21 15:15:58 +02:00
sh sh: convert nommu io{re,un}map() to static inline functions 2022-07-21 21:20:02 +02:00
sparc sparc: use fallback for random_get_entropy() instead of zero 2022-05-30 09:33:42 +02:00
um um: random: Don't initialise hwrng struct with zero 2022-08-21 15:16:00 +02:00
x86 x86/pmem: Fix platform-device leak in error path 2022-08-21 15:15:33 +02:00
xtensa xtensa: iss: fix handling error cases in iss_net_configure() 2022-08-21 15:15:59 +02:00
.gitignore
Kconfig arch/cc: Introduce a function to check for confidential computing features 2021-11-18 14:04:32 +01:00