Commit 3a38c57a authored by Linus Torvalds's avatar Linus Torvalds
Browse files

Merge tag 'perf-urgent-2023-10-01' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull perf event fixes from Ingo Molnar:
 "Misc fixes: work around an AMD microcode bug on certain models, and
  fix kexec kernel PMI handlers on AMD systems that get loaded on older
  kernels that have an unexpected register state"

* tag 'perf-urgent-2023-10-01' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
  perf/x86/amd: Do not WARN() on every IRQ
  perf/x86/amd/core: Fix overflow reset on hotplug
parents e402b086 599522d9
Loading
Loading
Loading
Loading
+17 −7
Original line number Diff line number Diff line
@@ -534,8 +534,12 @@ static void amd_pmu_cpu_reset(int cpu)
	/* Clear enable bits i.e. PerfCntrGlobalCtl.PerfCntrEn */
	wrmsrl(MSR_AMD64_PERF_CNTR_GLOBAL_CTL, 0);

	/* Clear overflow bits i.e. PerfCntrGLobalStatus.PerfCntrOvfl */
	wrmsrl(MSR_AMD64_PERF_CNTR_GLOBAL_STATUS_CLR, amd_pmu_global_cntr_mask);
	/*
	 * Clear freeze and overflow bits i.e. PerfCntrGLobalStatus.LbrFreeze
	 * and PerfCntrGLobalStatus.PerfCntrOvfl
	 */
	wrmsrl(MSR_AMD64_PERF_CNTR_GLOBAL_STATUS_CLR,
	       GLOBAL_STATUS_LBRS_FROZEN | amd_pmu_global_cntr_mask);
}

static int amd_pmu_cpu_prepare(int cpu)
@@ -570,6 +574,7 @@ static void amd_pmu_cpu_starting(int cpu)
	int i, nb_id;

	cpuc->perf_ctr_virt_mask = AMD64_EVENTSEL_HOSTONLY;
	amd_pmu_cpu_reset(cpu);

	if (!x86_pmu.amd_nb_constraints)
		return;
@@ -591,8 +596,6 @@ static void amd_pmu_cpu_starting(int cpu)

	cpuc->amd_nb->nb_id = nb_id;
	cpuc->amd_nb->refcnt++;

	amd_pmu_cpu_reset(cpu);
}

static void amd_pmu_cpu_dead(int cpu)
@@ -601,6 +604,7 @@ static void amd_pmu_cpu_dead(int cpu)

	kfree(cpuhw->lbr_sel);
	cpuhw->lbr_sel = NULL;
	amd_pmu_cpu_reset(cpu);

	if (!x86_pmu.amd_nb_constraints)
		return;
@@ -613,8 +617,6 @@ static void amd_pmu_cpu_dead(int cpu)

		cpuhw->amd_nb = NULL;
	}

	amd_pmu_cpu_reset(cpu);
}

static inline void amd_pmu_set_global_ctl(u64 ctl)
@@ -884,7 +886,7 @@ static int amd_pmu_v2_handle_irq(struct pt_regs *regs)
	struct hw_perf_event *hwc;
	struct perf_event *event;
	int handled = 0, idx;
	u64 status, mask;
	u64 reserved, status, mask;
	bool pmu_enabled;

	/*
@@ -909,6 +911,14 @@ static int amd_pmu_v2_handle_irq(struct pt_regs *regs)
		status &= ~GLOBAL_STATUS_LBRS_FROZEN;
	}

	reserved = status & ~amd_pmu_global_cntr_mask;
	if (reserved)
		pr_warn_once("Reserved PerfCntrGlobalStatus bits are set (0x%llx), please consider updating microcode\n",
			     reserved);

	/* Clear any reserved bits set by buggy microcode */
	status &= amd_pmu_global_cntr_mask;

	for (idx = 0; idx < x86_pmu.num_counters; idx++) {
		if (!test_bit(idx, cpuc->active_mask))
			continue;