Skip to content

Commit 1b94d31

Browse files
Kan LiangPeter Zijlstra
authored andcommitted
perf/x86/intel/uncore: Record the size of mapped area
Perf cannot validate an address before the actual access to MMIO space of some uncore units, e.g. IMC on TGL. Accessing an invalid address, which exceeds mapped area, can trigger oops. Perf never records the size of mapped area. Generic functions, e.g. uncore_mmio_read_counter(), cannot get the correct size for address validation. Add mmio_map_size in intel_uncore_type to record the size of mapped area. Print warning message if ioremap fails. Signed-off-by: Kan Liang <[email protected]> Signed-off-by: Peter Zijlstra (Intel) <[email protected]> Link: https://lkml.kernel.org/r/[email protected]
1 parent 2af834f commit 1b94d31

File tree

3 files changed

+21
-4
lines changed

3 files changed

+21
-4
lines changed

arch/x86/events/intel/uncore.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@ struct intel_uncore_type {
6161
unsigned msr_offset;
6262
unsigned mmio_offset;
6363
};
64+
unsigned mmio_map_size;
6465
unsigned num_shared_regs:8;
6566
unsigned single_fixed:1;
6667
unsigned pair_ctr_ctl:1;

arch/x86/events/intel/uncore_snb.c

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -426,6 +426,7 @@ static const struct attribute_group snb_uncore_imc_format_group = {
426426

427427
static void snb_uncore_imc_init_box(struct intel_uncore_box *box)
428428
{
429+
struct intel_uncore_type *type = box->pmu->type;
429430
struct pci_dev *pdev = box->pci_dev;
430431
int where = SNB_UNCORE_PCI_IMC_BAR_OFFSET;
431432
resource_size_t addr;
@@ -441,7 +442,10 @@ static void snb_uncore_imc_init_box(struct intel_uncore_box *box)
441442

442443
addr &= ~(PAGE_SIZE - 1);
443444

444-
box->io_addr = ioremap(addr, SNB_UNCORE_PCI_IMC_MAP_SIZE);
445+
box->io_addr = ioremap(addr, type->mmio_map_size);
446+
if (!box->io_addr)
447+
pr_warn("perf uncore: Failed to ioremap for %s.\n", type->name);
448+
445449
box->hrtimer_duration = UNCORE_SNB_IMC_HRTIMER_INTERVAL;
446450
}
447451

@@ -597,6 +601,7 @@ static struct intel_uncore_type snb_uncore_imc = {
597601
.num_counters = 2,
598602
.num_boxes = 1,
599603
.num_freerunning_types = SNB_PCI_UNCORE_IMC_FREERUNNING_TYPE_MAX,
604+
.mmio_map_size = SNB_UNCORE_PCI_IMC_MAP_SIZE,
600605
.freerunning = snb_uncore_imc_freerunning,
601606
.event_descs = snb_uncore_imc_events,
602607
.format_group = &snb_uncore_imc_format_group,
@@ -1157,6 +1162,7 @@ static void tgl_uncore_imc_freerunning_init_box(struct intel_uncore_box *box)
11571162
{
11581163
struct pci_dev *pdev = tgl_uncore_get_mc_dev();
11591164
struct intel_uncore_pmu *pmu = box->pmu;
1165+
struct intel_uncore_type *type = pmu->type;
11601166
resource_size_t addr;
11611167
u32 mch_bar;
11621168

@@ -1179,7 +1185,9 @@ static void tgl_uncore_imc_freerunning_init_box(struct intel_uncore_box *box)
11791185
addr |= ((resource_size_t)mch_bar << 32);
11801186
#endif
11811187

1182-
box->io_addr = ioremap(addr, TGL_UNCORE_PCI_IMC_MAP_SIZE);
1188+
box->io_addr = ioremap(addr, type->mmio_map_size);
1189+
if (!box->io_addr)
1190+
pr_warn("perf uncore: Failed to ioremap for %s.\n", type->name);
11831191
}
11841192

11851193
static struct intel_uncore_ops tgl_uncore_imc_freerunning_ops = {
@@ -1205,6 +1213,7 @@ static struct intel_uncore_type tgl_uncore_imc_free_running = {
12051213
.num_counters = 3,
12061214
.num_boxes = 2,
12071215
.num_freerunning_types = TGL_MMIO_UNCORE_IMC_FREERUNNING_TYPE_MAX,
1216+
.mmio_map_size = TGL_UNCORE_PCI_IMC_MAP_SIZE,
12081217
.freerunning = tgl_uncore_imc_freerunning,
12091218
.ops = &tgl_uncore_imc_freerunning_ops,
12101219
.event_descs = tgl_uncore_imc_events,

arch/x86/events/intel/uncore_snbep.c

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4421,6 +4421,7 @@ static void __snr_uncore_mmio_init_box(struct intel_uncore_box *box,
44214421
unsigned int box_ctl, int mem_offset)
44224422
{
44234423
struct pci_dev *pdev = snr_uncore_get_mc_dev(box->dieid);
4424+
struct intel_uncore_type *type = box->pmu->type;
44244425
resource_size_t addr;
44254426
u32 pci_dword;
44264427

@@ -4435,9 +4436,11 @@ static void __snr_uncore_mmio_init_box(struct intel_uncore_box *box,
44354436

44364437
addr += box_ctl;
44374438

4438-
box->io_addr = ioremap(addr, SNR_IMC_MMIO_SIZE);
4439-
if (!box->io_addr)
4439+
box->io_addr = ioremap(addr, type->mmio_map_size);
4440+
if (!box->io_addr) {
4441+
pr_warn("perf uncore: Failed to ioremap for %s.\n", type->name);
44404442
return;
4443+
}
44414444

44424445
writel(IVBEP_PMON_BOX_CTL_INT, box->io_addr);
44434446
}
@@ -4530,6 +4533,7 @@ static struct intel_uncore_type snr_uncore_imc = {
45304533
.event_mask = SNBEP_PMON_RAW_EVENT_MASK,
45314534
.box_ctl = SNR_IMC_MMIO_PMON_BOX_CTL,
45324535
.mmio_offset = SNR_IMC_MMIO_OFFSET,
4536+
.mmio_map_size = SNR_IMC_MMIO_SIZE,
45334537
.ops = &snr_uncore_mmio_ops,
45344538
.format_group = &skx_uncore_format_group,
45354539
};
@@ -4570,6 +4574,7 @@ static struct intel_uncore_type snr_uncore_imc_free_running = {
45704574
.num_counters = 3,
45714575
.num_boxes = 1,
45724576
.num_freerunning_types = SNR_IMC_FREERUNNING_TYPE_MAX,
4577+
.mmio_map_size = SNR_IMC_MMIO_SIZE,
45734578
.freerunning = snr_imc_freerunning,
45744579
.ops = &snr_uncore_imc_freerunning_ops,
45754580
.event_descs = snr_uncore_imc_freerunning_events,
@@ -4987,6 +4992,7 @@ static struct intel_uncore_type icx_uncore_imc = {
49874992
.event_mask = SNBEP_PMON_RAW_EVENT_MASK,
49884993
.box_ctl = SNR_IMC_MMIO_PMON_BOX_CTL,
49894994
.mmio_offset = SNR_IMC_MMIO_OFFSET,
4995+
.mmio_map_size = SNR_IMC_MMIO_SIZE,
49904996
.ops = &icx_uncore_mmio_ops,
49914997
.format_group = &skx_uncore_format_group,
49924998
};
@@ -5044,6 +5050,7 @@ static struct intel_uncore_type icx_uncore_imc_free_running = {
50445050
.num_counters = 5,
50455051
.num_boxes = 4,
50465052
.num_freerunning_types = ICX_IMC_FREERUNNING_TYPE_MAX,
5053+
.mmio_map_size = SNR_IMC_MMIO_SIZE,
50475054
.freerunning = icx_imc_freerunning,
50485055
.ops = &icx_uncore_imc_freerunning_ops,
50495056
.event_descs = icx_uncore_imc_freerunning_events,

0 commit comments

Comments
 (0)