perf: Allow storage of PMU private data in event
[deliverable/linux.git] / arch / x86 / events / intel / uncore.h
CommitLineData
087bfbb0
YZ
1#include <linux/module.h>
2#include <linux/slab.h>
14371cce 3#include <linux/pci.h>
087bfbb0 4#include <linux/perf_event.h>
27f6d22b 5#include "../perf_event.h"
087bfbb0
YZ
6
7#define UNCORE_PMU_NAME_LEN 32
7740dfc0 8#define UNCORE_PMU_HRTIMER_INTERVAL (60LL * NSEC_PER_SEC)
ced2efb0 9#define UNCORE_SNB_IMC_HRTIMER_INTERVAL (5ULL * NSEC_PER_SEC)
087bfbb0 10
eca26c99 11#define UNCORE_FIXED_EVENT 0xff
087bfbb0
YZ
12#define UNCORE_PMC_IDX_MAX_GENERIC 8
13#define UNCORE_PMC_IDX_FIXED UNCORE_PMC_IDX_MAX_GENERIC
14#define UNCORE_PMC_IDX_MAX (UNCORE_PMC_IDX_FIXED + 1)
15
899396cf
YZ
16#define UNCORE_PCI_DEV_DATA(type, idx) ((type << 8) | idx)
17#define UNCORE_PCI_DEV_TYPE(data) ((data >> 8) & 0xff)
18#define UNCORE_PCI_DEV_IDX(data) (data & 0xff)
19#define UNCORE_EXTRA_PCI_DEV 0xff
5306c31c 20#define UNCORE_EXTRA_PCI_DEV_MAX 3
899396cf
YZ
21
22/* support up to 8 sockets */
23#define UNCORE_SOCKET_MAX 8
24
087bfbb0
YZ
25#define UNCORE_EVENT_CONSTRAINT(c, n) EVENT_CONSTRAINT(c, n, 0xff)
26
27struct intel_uncore_ops;
28struct intel_uncore_pmu;
29struct intel_uncore_box;
30struct uncore_event_desc;
31
32struct intel_uncore_type {
33 const char *name;
34 int num_counters;
35 int num_boxes;
36 int perf_ctr_bits;
37 int fixed_ctr_bits;
087bfbb0
YZ
38 unsigned perf_ctr;
39 unsigned event_ctl;
40 unsigned event_mask;
41 unsigned fixed_ctr;
42 unsigned fixed_ctl;
43 unsigned box_ctl;
44 unsigned msr_offset;
6a67943a
YZ
45 unsigned num_shared_regs:8;
46 unsigned single_fixed:1;
254298c7 47 unsigned pair_ctr_ctl:1;
cb37af77 48 unsigned *msr_offsets;
087bfbb0
YZ
49 struct event_constraint unconstrainted;
50 struct event_constraint *constraints;
51 struct intel_uncore_pmu *pmus;
52 struct intel_uncore_ops *ops;
53 struct uncore_event_desc *event_descs;
314d9f63 54 const struct attribute_group *attr_groups[4];
d64b25b6 55 struct pmu *pmu; /* for custom pmu ops */
087bfbb0
YZ
56};
57
314d9f63
YZ
58#define pmu_group attr_groups[0]
59#define format_group attr_groups[1]
60#define events_group attr_groups[2]
087bfbb0
YZ
61
62struct intel_uncore_ops {
63 void (*init_box)(struct intel_uncore_box *);
a46195f1 64 void (*exit_box)(struct intel_uncore_box *);
087bfbb0
YZ
65 void (*disable_box)(struct intel_uncore_box *);
66 void (*enable_box)(struct intel_uncore_box *);
67 void (*disable_event)(struct intel_uncore_box *, struct perf_event *);
68 void (*enable_event)(struct intel_uncore_box *, struct perf_event *);
69 u64 (*read_counter)(struct intel_uncore_box *, struct perf_event *);
6a67943a
YZ
70 int (*hw_config)(struct intel_uncore_box *, struct perf_event *);
71 struct event_constraint *(*get_constraint)(struct intel_uncore_box *,
72 struct perf_event *);
73 void (*put_constraint)(struct intel_uncore_box *, struct perf_event *);
087bfbb0
YZ
74};
75
76struct intel_uncore_pmu {
4f089678
TG
77 struct pmu pmu;
78 char name[UNCORE_PMU_NAME_LEN];
79 int pmu_idx;
80 int func_id;
81 bool registered;
82 struct intel_uncore_type *type;
83 struct intel_uncore_box ** __percpu box;
84 struct list_head box_list;
087bfbb0
YZ
85};
86
6a67943a
YZ
87struct intel_uncore_extra_reg {
88 raw_spinlock_t lock;
254298c7 89 u64 config, config1, config2;
6a67943a
YZ
90 atomic_t ref;
91};
92
087bfbb0
YZ
93struct intel_uncore_box {
94 int phys_id;
95 int n_active; /* number of active events */
96 int n_events;
97 int cpu; /* cpu to collect events */
98 unsigned long flags;
99 atomic_t refcnt;
100 struct perf_event *events[UNCORE_PMC_IDX_MAX];
101 struct perf_event *event_list[UNCORE_PMC_IDX_MAX];
b371b594 102 struct event_constraint *event_constraint[UNCORE_PMC_IDX_MAX];
087bfbb0
YZ
103 unsigned long active_mask[BITS_TO_LONGS(UNCORE_PMC_IDX_MAX)];
104 u64 tags[UNCORE_PMC_IDX_MAX];
14371cce 105 struct pci_dev *pci_dev;
087bfbb0 106 struct intel_uncore_pmu *pmu;
79859cce 107 u64 hrtimer_duration; /* hrtimer timeout for this box */
087bfbb0
YZ
108 struct hrtimer hrtimer;
109 struct list_head list;
ced2efb0 110 struct list_head active_list;
b9e1ab6d 111 void *io_addr;
6a67943a 112 struct intel_uncore_extra_reg shared_regs[0];
087bfbb0
YZ
113};
114
115#define UNCORE_BOX_FLAG_INITIATED 0
116
117struct uncore_event_desc {
118 struct kobj_attribute attr;
119 const char *config;
120};
121
712df65c
TI
122struct pci2phy_map {
123 struct list_head list;
124 int segment;
125 int pbus_to_physid[256];
126};
127
712df65c
TI
128struct pci2phy_map *__find_pci2phy_map(int segment);
129
514b2346
YZ
130ssize_t uncore_event_show(struct kobject *kobj,
131 struct kobj_attribute *attr, char *buf);
132
087bfbb0
YZ
133#define INTEL_UNCORE_EVENT_DESC(_name, _config) \
134{ \
135 .attr = __ATTR(_name, 0444, uncore_event_show, NULL), \
136 .config = _config, \
137}
138
139#define DEFINE_UNCORE_FORMAT_ATTR(_var, _name, _format) \
140static ssize_t __uncore_##_var##_show(struct kobject *kobj, \
141 struct kobj_attribute *attr, \
142 char *page) \
143{ \
144 BUILD_BUG_ON(sizeof(_format) >= PAGE_SIZE); \
145 return sprintf(page, _format "\n"); \
146} \
147static struct kobj_attribute format_attr_##_var = \
148 __ATTR(_name, 0444, __uncore_##_var##_show, NULL)
149
14371cce
YZ
150static inline unsigned uncore_pci_box_ctl(struct intel_uncore_box *box)
151{
152 return box->pmu->type->box_ctl;
153}
154
155static inline unsigned uncore_pci_fixed_ctl(struct intel_uncore_box *box)
156{
157 return box->pmu->type->fixed_ctl;
158}
159
160static inline unsigned uncore_pci_fixed_ctr(struct intel_uncore_box *box)
161{
162 return box->pmu->type->fixed_ctr;
163}
164
165static inline
166unsigned uncore_pci_event_ctl(struct intel_uncore_box *box, int idx)
167{
168 return idx * 4 + box->pmu->type->event_ctl;
169}
170
171static inline
172unsigned uncore_pci_perf_ctr(struct intel_uncore_box *box, int idx)
173{
174 return idx * 8 + box->pmu->type->perf_ctr;
175}
176
cb37af77
YZ
177static inline unsigned uncore_msr_box_offset(struct intel_uncore_box *box)
178{
179 struct intel_uncore_pmu *pmu = box->pmu;
180 return pmu->type->msr_offsets ?
181 pmu->type->msr_offsets[pmu->pmu_idx] :
182 pmu->type->msr_offset * pmu->pmu_idx;
183}
184
185static inline unsigned uncore_msr_box_ctl(struct intel_uncore_box *box)
087bfbb0
YZ
186{
187 if (!box->pmu->type->box_ctl)
188 return 0;
cb37af77 189 return box->pmu->type->box_ctl + uncore_msr_box_offset(box);
087bfbb0
YZ
190}
191
cb37af77 192static inline unsigned uncore_msr_fixed_ctl(struct intel_uncore_box *box)
087bfbb0
YZ
193{
194 if (!box->pmu->type->fixed_ctl)
195 return 0;
cb37af77 196 return box->pmu->type->fixed_ctl + uncore_msr_box_offset(box);
087bfbb0
YZ
197}
198
cb37af77 199static inline unsigned uncore_msr_fixed_ctr(struct intel_uncore_box *box)
087bfbb0 200{
cb37af77 201 return box->pmu->type->fixed_ctr + uncore_msr_box_offset(box);
087bfbb0
YZ
202}
203
204static inline
205unsigned uncore_msr_event_ctl(struct intel_uncore_box *box, int idx)
206{
254298c7
YZ
207 return box->pmu->type->event_ctl +
208 (box->pmu->type->pair_ctr_ctl ? 2 * idx : idx) +
cb37af77 209 uncore_msr_box_offset(box);
087bfbb0
YZ
210}
211
212static inline
213unsigned uncore_msr_perf_ctr(struct intel_uncore_box *box, int idx)
214{
254298c7
YZ
215 return box->pmu->type->perf_ctr +
216 (box->pmu->type->pair_ctr_ctl ? 2 * idx : idx) +
cb37af77 217 uncore_msr_box_offset(box);
087bfbb0
YZ
218}
219
14371cce
YZ
220static inline
221unsigned uncore_fixed_ctl(struct intel_uncore_box *box)
222{
223 if (box->pci_dev)
224 return uncore_pci_fixed_ctl(box);
225 else
226 return uncore_msr_fixed_ctl(box);
227}
228
229static inline
230unsigned uncore_fixed_ctr(struct intel_uncore_box *box)
231{
232 if (box->pci_dev)
233 return uncore_pci_fixed_ctr(box);
234 else
235 return uncore_msr_fixed_ctr(box);
236}
237
238static inline
239unsigned uncore_event_ctl(struct intel_uncore_box *box, int idx)
240{
241 if (box->pci_dev)
242 return uncore_pci_event_ctl(box, idx);
243 else
244 return uncore_msr_event_ctl(box, idx);
245}
246
247static inline
248unsigned uncore_perf_ctr(struct intel_uncore_box *box, int idx)
249{
250 if (box->pci_dev)
251 return uncore_pci_perf_ctr(box, idx);
252 else
253 return uncore_msr_perf_ctr(box, idx);
254}
255
087bfbb0
YZ
256static inline int uncore_perf_ctr_bits(struct intel_uncore_box *box)
257{
258 return box->pmu->type->perf_ctr_bits;
259}
260
261static inline int uncore_fixed_ctr_bits(struct intel_uncore_box *box)
262{
263 return box->pmu->type->fixed_ctr_bits;
264}
265
266static inline int uncore_num_counters(struct intel_uncore_box *box)
267{
268 return box->pmu->type->num_counters;
269}
270
271static inline void uncore_disable_box(struct intel_uncore_box *box)
272{
273 if (box->pmu->type->ops->disable_box)
274 box->pmu->type->ops->disable_box(box);
275}
276
277static inline void uncore_enable_box(struct intel_uncore_box *box)
278{
279 if (box->pmu->type->ops->enable_box)
280 box->pmu->type->ops->enable_box(box);
281}
282
283static inline void uncore_disable_event(struct intel_uncore_box *box,
284 struct perf_event *event)
285{
286 box->pmu->type->ops->disable_event(box, event);
287}
288
289static inline void uncore_enable_event(struct intel_uncore_box *box,
290 struct perf_event *event)
291{
292 box->pmu->type->ops->enable_event(box, event);
293}
294
295static inline u64 uncore_read_counter(struct intel_uncore_box *box,
296 struct perf_event *event)
297{
298 return box->pmu->type->ops->read_counter(box, event);
299}
300
15c12479
IM
301static inline void uncore_box_init(struct intel_uncore_box *box)
302{
303 if (!test_and_set_bit(UNCORE_BOX_FLAG_INITIATED, &box->flags)) {
304 if (box->pmu->type->ops->init_box)
305 box->pmu->type->ops->init_box(box);
306 }
307}
308
a46195f1
TG
309static inline void uncore_box_exit(struct intel_uncore_box *box)
310{
311 if (test_and_clear_bit(UNCORE_BOX_FLAG_INITIATED, &box->flags)) {
312 if (box->pmu->type->ops->exit_box)
313 box->pmu->type->ops->exit_box(box);
314 }
315}
316
254298c7
YZ
317static inline bool uncore_box_is_fake(struct intel_uncore_box *box)
318{
319 return (box->phys_id < 0);
320}
514b2346
YZ
321
322struct intel_uncore_pmu *uncore_event_to_pmu(struct perf_event *event);
323struct intel_uncore_box *uncore_pmu_to_box(struct intel_uncore_pmu *pmu, int cpu);
324struct intel_uncore_box *uncore_event_to_box(struct perf_event *event);
325u64 uncore_msr_read_counter(struct intel_uncore_box *box, struct perf_event *event);
326void uncore_pmu_start_hrtimer(struct intel_uncore_box *box);
327void uncore_pmu_cancel_hrtimer(struct intel_uncore_box *box);
328void uncore_pmu_event_read(struct perf_event *event);
329void uncore_perf_event_update(struct intel_uncore_box *box, struct perf_event *event);
330struct event_constraint *
331uncore_get_constraint(struct intel_uncore_box *box, struct perf_event *event);
332void uncore_put_constraint(struct intel_uncore_box *box, struct perf_event *event);
333u64 uncore_shared_reg_config(struct intel_uncore_box *box, int idx);
334
335extern struct intel_uncore_type **uncore_msr_uncores;
336extern struct intel_uncore_type **uncore_pci_uncores;
337extern struct pci_driver *uncore_pci_driver;
712df65c
TI
338extern raw_spinlock_t pci2phy_map_lock;
339extern struct list_head pci2phy_map_head;
514b2346
YZ
340extern struct pci_dev *uncore_extra_pci_dev[UNCORE_SOCKET_MAX][UNCORE_EXTRA_PCI_DEV_MAX];
341extern struct event_constraint uncore_constraint_empty;
92807ffd
YZ
342
343/* perf_event_intel_uncore_snb.c */
344int snb_uncore_pci_init(void);
345int ivb_uncore_pci_init(void);
346int hsw_uncore_pci_init(void);
a41f3c8c 347int bdw_uncore_pci_init(void);
0e1eb0a1 348int skl_uncore_pci_init(void);
92807ffd
YZ
349void snb_uncore_cpu_init(void);
350void nhm_uncore_cpu_init(void);
77af0037 351int snb_pci2phy_map_init(int devid);
8268fdfc
YZ
352
353/* perf_event_intel_uncore_snbep.c */
354int snbep_uncore_pci_init(void);
355void snbep_uncore_cpu_init(void);
ddcd0973
PZ
356int ivbep_uncore_pci_init(void);
357void ivbep_uncore_cpu_init(void);
e735b9db
YZ
358int hswep_uncore_pci_init(void);
359void hswep_uncore_cpu_init(void);
070e9887
KL
360int bdx_uncore_pci_init(void);
361void bdx_uncore_cpu_init(void);
77af0037
HC
362int knl_uncore_pci_init(void);
363void knl_uncore_cpu_init(void);
c1e46580
YZ
364
365/* perf_event_intel_uncore_nhmex.c */
366void nhmex_uncore_cpu_init(void);
This page took 0.256189 seconds and 5 git commands to generate.