]> rtime.felk.cvut.cz Git - sojka/nv-tegra/linux-3.10.git/blob - include/linux/tegra_profiler.h
tegra-profiler: add access to the exception tables
[sojka/nv-tegra/linux-3.10.git] / include / linux / tegra_profiler.h
1 /*
2  * include/linux/tegra_profiler.h
3  *
4  * Copyright (c) 2014, NVIDIA CORPORATION.  All rights reserved.
5  *
6  * This program is free software; you can redistribute it and/or modify it
7  * under the terms and conditions of the GNU General Public License,
8  * version 2, as published by the Free Software Foundation.
9  *
10  * This program is distributed in the hope it will be useful, but WITHOUT
11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
13  * more details.
14  *
15  */
16
17 #ifndef __TEGRA_PROFILER_H
18 #define __TEGRA_PROFILER_H
19
20 #include <linux/ioctl.h>
21
22 #define QUADD_SAMPLES_VERSION   25
23 #define QUADD_IO_VERSION        12
24
25 #define QUADD_IO_VERSION_DYNAMIC_RB             5
26 #define QUADD_IO_VERSION_RB_MAX_FILL_COUNT      6
27 #define QUADD_IO_VERSION_MOD_STATE_STATUS_FIELD 7
28 #define QUADD_IO_VERSION_BT_KERNEL_CTX          8
29 #define QUADD_IO_VERSION_GET_MMAP               9
30 #define QUADD_IO_VERSION_BT_UNWIND_TABLES       10
31 #define QUADD_IO_VERSION_UNWIND_MIXED           11
32 #define QUADD_IO_VERSION_EXTABLES_MMAP          12
33
34 #define QUADD_SAMPLE_VERSION_THUMB_MODE_FLAG    17
35 #define QUADD_SAMPLE_VERSION_GROUP_SAMPLES      18
36 #define QUADD_SAMPLE_VERSION_THREAD_STATE_FLD   19
37 #define QUADD_SAMPLE_VERSION_BT_UNWIND_TABLES   22
38 #define QUADD_SAMPLE_VERSION_SUPPORT_IP64       23
39 #define QUADD_SAMPLE_VERSION_SPECIAL_MMAP       24
40 #define QUADD_SAMPLE_VERSION_UNWIND_MIXED       25
41
42 #define QUADD_MAX_COUNTERS      32
43 #define QUADD_MAX_PROCESS       64
44
45 #define QUADD_DEVICE_NAME       "quadd"
46 #define QUADD_AUTH_DEVICE_NAME  "quadd_auth"
47
48 #define QUADD_MOD_DEVICE_NAME           "quadd_mod"
49 #define QUADD_MOD_AUTH_DEVICE_NAME      "quadd_mod_auth"
50
51 #define QUADD_IOCTL     100
52
53 /*
54  * Setup params (profiling frequency, etc.)
55  */
56 #define IOCTL_SETUP _IOW(QUADD_IOCTL, 0, struct quadd_parameters)
57
58 /*
59  * Start profiling.
60  */
61 #define IOCTL_START _IO(QUADD_IOCTL, 1)
62
63 /*
64  * Stop profiling.
65  */
66 #define IOCTL_STOP _IO(QUADD_IOCTL, 2)
67
68 /*
69  * Getting capabilities
70  */
71 #define IOCTL_GET_CAP _IOR(QUADD_IOCTL, 3, struct quadd_comm_cap)
72
73 /*
74  * Getting state of module
75  */
76 #define IOCTL_GET_STATE _IOR(QUADD_IOCTL, 4, struct quadd_module_state)
77
78 /*
79  * Getting version of module
80  */
81 #define IOCTL_GET_VERSION _IOR(QUADD_IOCTL, 5, struct quadd_module_version)
82
83 /*
84  * Send exception-handling tables info
85  */
86 #define IOCTL_SET_EXTAB _IOW(QUADD_IOCTL, 6, struct quadd_extables)
87
88 #define QUADD_CPUMODE_TEGRA_POWER_CLUSTER_LP    (1 << 29)       /* LP CPU */
89 #define QUADD_CPUMODE_THUMB                     (1 << 30)       /* thumb mode */
90
91 enum quadd_events_id {
92         QUADD_EVENT_TYPE_CPU_CYCLES = 0,
93
94         QUADD_EVENT_TYPE_INSTRUCTIONS,
95         QUADD_EVENT_TYPE_BRANCH_INSTRUCTIONS,
96         QUADD_EVENT_TYPE_BRANCH_MISSES,
97         QUADD_EVENT_TYPE_BUS_CYCLES,
98
99         QUADD_EVENT_TYPE_L1_DCACHE_READ_MISSES,
100         QUADD_EVENT_TYPE_L1_DCACHE_WRITE_MISSES,
101         QUADD_EVENT_TYPE_L1_ICACHE_MISSES,
102
103         QUADD_EVENT_TYPE_L2_DCACHE_READ_MISSES,
104         QUADD_EVENT_TYPE_L2_DCACHE_WRITE_MISSES,
105         QUADD_EVENT_TYPE_L2_ICACHE_MISSES,
106
107         QUADD_EVENT_TYPE_MAX,
108 };
109
110 struct event_data {
111         int event_source;
112         int event_id;
113
114         u32 val;
115         u32 prev_val;
116 };
117
118 enum quadd_record_type {
119         QUADD_RECORD_TYPE_SAMPLE = 1,
120         QUADD_RECORD_TYPE_MMAP,
121         QUADD_RECORD_TYPE_MA,
122         QUADD_RECORD_TYPE_COMM,
123         QUADD_RECORD_TYPE_DEBUG,
124         QUADD_RECORD_TYPE_HEADER,
125         QUADD_RECORD_TYPE_POWER_RATE,
126         QUADD_RECORD_TYPE_ADDITIONAL_SAMPLE,
127 };
128
129 enum quadd_event_source {
130         QUADD_EVENT_SOURCE_PMU = 1,
131         QUADD_EVENT_SOURCE_PL310,
132 };
133
134 enum quadd_cpu_mode {
135         QUADD_CPU_MODE_KERNEL = 1,
136         QUADD_CPU_MODE_USER,
137         QUADD_CPU_MODE_NONE,
138 };
139
140 #pragma pack(push, 1)
141
142 #define QUADD_SAMPLE_UNW_METHOD_SHIFT   0
143 #define QUADD_SAMPLE_UNW_METHOD_MASK    (1 << QUADD_SAMPLE_UNW_METHOD_SHIFT)
144
145 enum {
146         QUADD_UNW_METHOD_FP = 0,
147         QUADD_UNW_METHOD_EHT,
148         QUADD_UNW_METHOD_MIXED,
149 };
150
151 #define QUADD_SAMPLE_URC_SHIFT          1
152 #define QUADD_SAMPLE_URC_MASK           (0x0f << QUADD_SAMPLE_URC_SHIFT)
153
154 enum {
155         QUADD_URC_SUCCESS = 0,
156         QUADD_URC_FAILURE,
157         QUADD_URC_IDX_NOT_FOUND,
158         QUADD_URC_TBL_NOT_EXIST,
159         QUADD_URC_EACCESS,
160         QUADD_URC_TBL_IS_CORRUPT,
161         QUADD_URC_CANTUNWIND,
162         QUADD_URC_UNHANDLED_INSTRUCTION,
163         QUADD_URC_REFUSE_TO_UNWIND,
164         QUADD_URC_SP_INCORRECT,
165         QUADD_URC_SPARE_ENCODING,
166         QUADD_URC_UNSUPPORTED_PR,
167         QUADD_URC_PC_INCORRECT,
168         QUADD_URC_MAX,
169 };
170
171 #define QUADD_SED_IP64                  (1 << 0)
172
173 #define QUADD_SED_UNW_METHOD_SHIFT      1
174 #define QUADD_SED_UNW_METHOD_MASK       (0x07 << QUADD_SED_UNW_METHOD_SHIFT)
175
176 struct quadd_sample_data {
177         u64 ip;
178         u32 pid;
179         u64 time;
180
181         u16     cpu:6,
182                 user_mode:1,
183                 lp_mode:1,
184                 thumb_mode:1,
185                 state:1,
186                 in_interrupt:1,
187                 reserved:5;
188
189         u8 callchain_nr;
190         u32 events_flags;
191 };
192
193 #define QUADD_MMAP_ED_IS_FILE_EXISTS    (1 << 0)
194
195 struct quadd_mmap_data {
196         u32 pid;
197
198         u64 addr;
199         u64 len;
200
201         u8 user_mode:1;
202         u16 filename_length;
203 };
204
205 struct quadd_ma_data {
206         u32 pid;
207         u64 time;
208
209         u32 vm_size;
210         u32 rss_size;
211 };
212
213 struct quadd_power_rate_data {
214         u64 time;
215
216         u8 nr_cpus;
217
218         u32 gpu;
219         u32 emc;
220 };
221
222 struct quadd_additional_sample {
223         u8 type;
224
225         u32 values[6];
226         u16 extra_length;
227 };
228
229 enum {
230         QM_DEBUG_SAMPLE_TYPE_SCHED_IN = 1,
231         QM_DEBUG_SAMPLE_TYPE_SCHED_OUT,
232
233         QM_DEBUG_SAMPLE_TYPE_TIMER_HANDLE,
234         QM_DEBUG_SAMPLE_TYPE_TIMER_START,
235         QM_DEBUG_SAMPLE_TYPE_TIMER_CANCEL,
236         QM_DEBUG_SAMPLE_TYPE_TIMER_FORWARD,
237
238         QM_DEBUG_SAMPLE_TYPE_READ_COUNTER,
239
240         QM_DEBUG_SAMPLE_TYPE_SOURCE_START,
241         QM_DEBUG_SAMPLE_TYPE_SOURCE_STOP,
242 };
243
244 struct quadd_debug_data {
245         u8 type;
246
247         u32 pid;
248         u64 time;
249
250         u16     cpu:6,
251                 user_mode:1,
252                 lp_mode:1,
253                 thumb_mode:1,
254                 reserved:7;
255
256         u32 extra_value[2];
257         u16 extra_length;
258 };
259
260 #define QUADD_HEADER_MAGIC      0x1122
261
262 struct quadd_header_data {
263         u16 magic;
264         u16 version;
265
266         u32     backtrace:1,
267                 use_freq:1,
268                 system_wide:1,
269                 power_rate:1,
270                 debug_samples:1,
271                 get_mmap:1,
272                 reserved:26;    /* reserved fields for future extensions */
273
274         u32 freq;
275         u16 ma_freq;
276         u16 power_rate_freq;
277
278         u8 nr_events;
279         u16 extra_length;
280 };
281
282 struct quadd_record_data {
283         u8 record_type;
284
285         /* sample: it should be the biggest size */
286         union {
287                 struct quadd_sample_data        sample;
288                 struct quadd_mmap_data          mmap;
289                 struct quadd_ma_data            ma;
290                 struct quadd_debug_data         debug;
291                 struct quadd_header_data        hdr;
292                 struct quadd_power_rate_data    power_rate;
293                 struct quadd_additional_sample  additional_sample;
294         };
295 } __aligned(4);
296
297 #pragma pack(4)
298
299 #define QUADD_MAX_PACKAGE_NAME  320
300
301 enum {
302         QUADD_PARAM_IDX_SIZE_OF_RB      = 0,
303         QUADD_PARAM_IDX_EXTRA           = 1,
304 };
305
306 #define QUADD_PARAM_EXTRA_GET_MMAP              (1 << 0)
307 #define QUADD_PARAM_EXTRA_BT_FP                 (1 << 1)
308 #define QUADD_PARAM_EXTRA_BT_UNWIND_TABLES      (1 << 2)
309 #define QUADD_PARAM_EXTRA_BT_MIXED              (1 << 3)
310
311 struct quadd_parameters {
312         u32 freq;
313         u32 ma_freq;
314         u32 power_rate_freq;
315
316         u64     backtrace:1,
317                 use_freq:1,
318                 system_wide:1,
319                 debug_samples:1;
320
321         u32 pids[QUADD_MAX_PROCESS];
322         u32 nr_pids;
323
324         u8 package_name[QUADD_MAX_PACKAGE_NAME];
325
326         u32 events[QUADD_MAX_COUNTERS];
327         u32 nr_events;
328
329         u32 reserved[16];       /* reserved fields for future extensions */
330 };
331
332 struct quadd_events_cap {
333         u32     cpu_cycles:1,
334                 instructions:1,
335                 branch_instructions:1,
336                 branch_misses:1,
337                 bus_cycles:1,
338
339                 l1_dcache_read_misses:1,
340                 l1_dcache_write_misses:1,
341                 l1_icache_misses:1,
342
343                 l2_dcache_read_misses:1,
344                 l2_dcache_write_misses:1,
345                 l2_icache_misses:1;
346 };
347
348 enum {
349         QUADD_COMM_CAP_IDX_EXTRA = 0,
350 };
351
352 #define QUADD_COMM_CAP_EXTRA_BT_KERNEL_CTX      (1 << 0)
353 #define QUADD_COMM_CAP_EXTRA_GET_MMAP           (1 << 1)
354 #define QUADD_COMM_CAP_EXTRA_GROUP_SAMPLES      (1 << 2)
355 #define QUADD_COMM_CAP_EXTRA_BT_UNWIND_TABLES   (1 << 3)
356 #define QUADD_COMM_CAP_EXTRA_SUPPORT_AARCH64    (1 << 4)
357 #define QUADD_COMM_CAP_EXTRA_SPECIAL_ARCH_MMAP  (1 << 5)
358 #define QUADD_COMM_CAP_EXTRA_UNWIND_MIXED       (1 << 6)
359
360 struct quadd_comm_cap {
361         u32     pmu:1,
362                 power_rate:1,
363                 l2_cache:1,
364                 l2_multiple_events:1,
365                 tegra_lp_cluster:1,
366                 blocked_read:1;
367
368         struct quadd_events_cap events_cap;
369
370         u32 reserved[16];       /* reserved fields for future extensions */
371 };
372
373 enum {
374         QUADD_MOD_STATE_IDX_RB_MAX_FILL_COUNT = 0,
375         QUADD_MOD_STATE_IDX_STATUS,
376 };
377
378 #define QUADD_MOD_STATE_STATUS_IS_ACTIVE        (1 << 0)
379 #define QUADD_MOD_STATE_STATUS_IS_AUTH_OPEN     (1 << 1)
380
381 struct quadd_module_state {
382         u64 nr_all_samples;
383         u64 nr_skipped_samples;
384
385         u32 buffer_size;
386         u32 buffer_fill_size;
387
388         u32 reserved[16];       /* reserved fields for future extensions */
389 };
390
391 struct quadd_module_version {
392         u8 branch[32];
393         u8 version[16];
394
395         u32 samples_version;
396         u32 io_version;
397
398         u32 reserved[4];        /* reserved fields for future extensions */
399 };
400
401 struct quadd_sec_info {
402         u64 addr;
403         u64 length;
404 };
405
406 enum {
407         QUADD_EXT_IDX_EXTAB_OFFSET = 0,
408         QUADD_EXT_IDX_EXIDX_OFFSET = 1,
409         QUADD_EXT_IDX_MMAP_VM_START = 2,
410 };
411
412 struct quadd_extables {
413         u64 vm_start;
414         u64 vm_end;
415
416         struct quadd_sec_info extab;
417         struct quadd_sec_info exidx;
418
419         u32 reserved[4];        /* reserved fields for future extensions */
420 };
421
422 #pragma pack(pop)
423
424 #ifdef __KERNEL__
425
426 struct task_struct;
427 struct vm_area_struct;
428
429 #ifdef CONFIG_TEGRA_PROFILER
430 extern void __quadd_task_sched_in(struct task_struct *prev,
431                                   struct task_struct *task);
432 extern void __quadd_task_sched_out(struct task_struct *prev,
433                                    struct task_struct *next);
434
435 extern void __quadd_event_mmap(struct vm_area_struct *vma);
436
437 static inline void quadd_task_sched_in(struct task_struct *prev,
438                                        struct task_struct *task)
439 {
440         __quadd_task_sched_in(prev, task);
441 }
442
443 static inline void quadd_task_sched_out(struct task_struct *prev,
444                                         struct task_struct *next)
445 {
446         __quadd_task_sched_out(prev, next);
447 }
448
449 static inline void quadd_event_mmap(struct vm_area_struct *vma)
450 {
451         __quadd_event_mmap(vma);
452 }
453
454 #else   /* CONFIG_TEGRA_PROFILER */
455
456 static inline void quadd_task_sched_in(struct task_struct *prev,
457                                        struct task_struct *task)
458 {
459 }
460
461 static inline void quadd_task_sched_out(struct task_struct *prev,
462                                         struct task_struct *next)
463 {
464 }
465
466 static inline void quadd_event_mmap(struct vm_area_struct *vma)
467 {
468 }
469
470 #endif  /* CONFIG_TEGRA_PROFILER */
471
472 #endif  /* __KERNEL__ */
473
474 #endif  /* __TEGRA_PROFILER_H */