15205e777550cb1c6b772195984228545e3fb771
[linux-2.6.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   20
23 #define QUADD_IO_VERSION        9
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
31 #define QUADD_SAMPLE_VERSION_THUMB_MODE_FLAG    17
32 #define QUADD_SAMPLE_VERSION_GROUP_SAMPLES      18
33 #define QUADD_SAMPLE_VERSION_THREAD_STATE_FLD   19
34
35 #define QUADD_MAX_COUNTERS      32
36 #define QUADD_MAX_PROCESS       64
37
38 #define QUADD_DEVICE_NAME       "quadd"
39 #define QUADD_AUTH_DEVICE_NAME  "quadd_auth"
40
41 #define QUADD_MOD_DEVICE_NAME           "quadd_mod"
42 #define QUADD_MOD_AUTH_DEVICE_NAME      "quadd_mod_auth"
43
44 #define QUADD_IOCTL     100
45
46 /*
47  * Setup params (profiling frequency, etc.)
48  */
49 #define IOCTL_SETUP _IOW(QUADD_IOCTL, 0, struct quadd_parameters)
50
51 /*
52  * Start profiling.
53  */
54 #define IOCTL_START _IO(QUADD_IOCTL, 1)
55
56 /*
57  * Stop profiling.
58  */
59 #define IOCTL_STOP _IO(QUADD_IOCTL, 2)
60
61 /*
62  * Getting capabilities
63  */
64 #define IOCTL_GET_CAP _IOR(QUADD_IOCTL, 3, struct quadd_comm_cap)
65
66 /*
67  * Getting state of module
68  */
69 #define IOCTL_GET_STATE _IOR(QUADD_IOCTL, 4, struct quadd_module_state)
70
71 /*
72  * Getting version of module
73  */
74 #define IOCTL_GET_VERSION _IOR(QUADD_IOCTL, 5, struct quadd_module_version)
75
76
77 #define QUADD_HRT_SCHED_IN_FUNC         "finish_task_switch"
78
79 #define QUADD_CPUMODE_TEGRA_POWER_CLUSTER_LP    (1 << 29)       /* LP CPU */
80 #define QUADD_CPUMODE_THUMB                     (1 << 30)       /* thumb mode */
81
82 enum quadd_events_id {
83         QUADD_EVENT_TYPE_CPU_CYCLES = 0,
84
85         QUADD_EVENT_TYPE_INSTRUCTIONS,
86         QUADD_EVENT_TYPE_BRANCH_INSTRUCTIONS,
87         QUADD_EVENT_TYPE_BRANCH_MISSES,
88         QUADD_EVENT_TYPE_BUS_CYCLES,
89
90         QUADD_EVENT_TYPE_L1_DCACHE_READ_MISSES,
91         QUADD_EVENT_TYPE_L1_DCACHE_WRITE_MISSES,
92         QUADD_EVENT_TYPE_L1_ICACHE_MISSES,
93
94         QUADD_EVENT_TYPE_L2_DCACHE_READ_MISSES,
95         QUADD_EVENT_TYPE_L2_DCACHE_WRITE_MISSES,
96         QUADD_EVENT_TYPE_L2_ICACHE_MISSES,
97
98         QUADD_EVENT_TYPE_MAX,
99 };
100
101 struct event_data {
102         int event_source;
103         int event_id;
104
105         u32 val;
106         u32 prev_val;
107 };
108
109 enum quadd_record_type {
110         QUADD_RECORD_TYPE_SAMPLE = 1,
111         QUADD_RECORD_TYPE_MMAP,
112         QUADD_RECORD_TYPE_MA,
113         QUADD_RECORD_TYPE_COMM,
114         QUADD_RECORD_TYPE_DEBUG,
115         QUADD_RECORD_TYPE_HEADER,
116         QUADD_RECORD_TYPE_POWER_RATE,
117         QUADD_RECORD_TYPE_ADDITIONAL_SAMPLE,
118 };
119
120 enum quadd_event_source {
121         QUADD_EVENT_SOURCE_PMU = 1,
122         QUADD_EVENT_SOURCE_PL310,
123 };
124
125 enum quadd_cpu_mode {
126         QUADD_CPU_MODE_KERNEL = 1,
127         QUADD_CPU_MODE_USER,
128         QUADD_CPU_MODE_NONE,
129 };
130
131 typedef u32 quadd_bt_addr_t;
132
133 #pragma pack(push, 1)
134
135 struct quadd_sample_data {
136         u64 ip;
137         u32 pid;
138         u64 time;
139
140         u16     cpu:6,
141                 user_mode:1,
142                 lp_mode:1,
143                 thumb_mode:1,
144                 state:1,
145                 in_interrupt:1,
146                 reserved:5;
147
148         u8 callchain_nr;
149         u32 events_flags;
150 };
151
152 struct quadd_mmap_data {
153         u32 pid;
154
155         u64 addr;
156         u64 len;
157
158         u8 user_mode:1;
159         u16 filename_length;
160 };
161
162 struct quadd_ma_data {
163         u32 pid;
164         u64 time;
165
166         u32 vm_size;
167         u32 rss_size;
168 };
169
170 struct quadd_power_rate_data {
171         u64 time;
172
173         u8 nr_cpus;
174
175         u32 gpu;
176         u32 emc;
177 };
178
179 struct quadd_additional_sample {
180         u8 type;
181
182         u32 values[6];
183         u16 extra_length;
184 };
185
186 enum {
187         QM_DEBUG_SAMPLE_TYPE_SCHED_IN = 1,
188         QM_DEBUG_SAMPLE_TYPE_SCHED_OUT,
189
190         QM_DEBUG_SAMPLE_TYPE_TIMER_HANDLE,
191         QM_DEBUG_SAMPLE_TYPE_TIMER_START,
192         QM_DEBUG_SAMPLE_TYPE_TIMER_CANCEL,
193         QM_DEBUG_SAMPLE_TYPE_TIMER_FORWARD,
194
195         QM_DEBUG_SAMPLE_TYPE_READ_COUNTER,
196
197         QM_DEBUG_SAMPLE_TYPE_SOURCE_START,
198         QM_DEBUG_SAMPLE_TYPE_SOURCE_STOP,
199 };
200
201 struct quadd_debug_data {
202         u8 type;
203
204         u32 pid;
205         u64 time;
206
207         u16     cpu:6,
208                 user_mode:1,
209                 lp_mode:1,
210                 thumb_mode:1,
211                 reserved:7;
212
213         u32 extra_value[2];
214         u16 extra_length;
215 };
216
217 #define QUADD_HEADER_MAGIC      0x1122
218
219 struct quadd_header_data {
220         u16 magic;
221         u16 version;
222
223         u32     backtrace:1,
224                 use_freq:1,
225                 system_wide:1,
226                 power_rate:1,
227                 debug_samples:1,
228                 get_mmap:1,
229                 reserved:26;    /* reserved fields for future extensions */
230
231         u32 freq;
232         u16 ma_freq;
233         u16 power_rate_freq;
234
235         u8 nr_events;
236         u16 extra_length;
237 };
238
239 #define QUADD_RECORD_MAGIC      0x335577aa
240
241 struct quadd_record_data {
242         u32 magic;      /* temporary, it will be removed later */
243         u8 record_type;
244
245         union {
246                 struct quadd_sample_data        sample;
247                 struct quadd_mmap_data          mmap;
248                 struct quadd_ma_data            ma;
249                 struct quadd_debug_data         debug;
250                 struct quadd_header_data        hdr;
251                 struct quadd_power_rate_data    power_rate;
252                 struct quadd_additional_sample  additional_sample;
253         };
254 } __aligned(4);
255
256 #pragma pack(4)
257
258 #define QUADD_MAX_PACKAGE_NAME  320
259
260 enum {
261         QUADD_PARAM_IDX_SIZE_OF_RB      = 0,
262         QUADD_PARAM_IDX_EXTRA           = 1,
263 };
264
265 #define QUADD_PARAM_IDX_EXTRA_GET_MMAP  (1 << 0)
266
267 struct quadd_parameters {
268         u32 freq;
269         u32 ma_freq;
270         u32 power_rate_freq;
271
272         u64     backtrace:1,
273                 use_freq:1,
274                 system_wide:1,
275                 debug_samples:1;
276
277         u32 pids[QUADD_MAX_PROCESS];
278         u32 nr_pids;
279
280         u8 package_name[QUADD_MAX_PACKAGE_NAME];
281
282         u32 events[QUADD_MAX_COUNTERS];
283         u32 nr_events;
284
285         u32 reserved[16];       /* reserved fields for future extensions */
286 };
287
288 struct quadd_events_cap {
289         u32     cpu_cycles:1,
290                 instructions:1,
291                 branch_instructions:1,
292                 branch_misses:1,
293                 bus_cycles:1,
294
295                 l1_dcache_read_misses:1,
296                 l1_dcache_write_misses:1,
297                 l1_icache_misses:1,
298
299                 l2_dcache_read_misses:1,
300                 l2_dcache_write_misses:1,
301                 l2_icache_misses:1;
302 };
303
304 enum {
305         QUADD_COMM_CAP_IDX_EXTRA = 0,
306 };
307
308 #define QUADD_COMM_CAP_EXTRA_BT_KERNEL_CTX      (1 << 0)
309 #define QUADD_COMM_CAP_EXTRA_GET_MMAP           (1 << 1)
310 #define QUADD_COMM_CAP_EXTRA_GROUP_SAMPLES      (1 << 2)
311
312 struct quadd_comm_cap {
313         u32     pmu:1,
314                 power_rate:1,
315                 l2_cache:1,
316                 l2_multiple_events:1,
317                 tegra_lp_cluster:1,
318                 blocked_read:1;
319
320         struct quadd_events_cap events_cap;
321
322         u32 reserved[16];       /* reserved fields for future extensions */
323 };
324
325 enum {
326         QUADD_MOD_STATE_IDX_RB_MAX_FILL_COUNT = 0,
327         QUADD_MOD_STATE_IDX_STATUS,
328 };
329
330 #define QUADD_MOD_STATE_STATUS_IS_ACTIVE        (1 << 0)
331 #define QUADD_MOD_STATE_STATUS_IS_AUTH_OPEN     (1 << 1)
332
333 struct quadd_module_state {
334         u64 nr_all_samples;
335         u64 nr_skipped_samples;
336
337         u32 buffer_size;
338         u32 buffer_fill_size;
339
340         u32 reserved[16];       /* reserved fields for future extensions */
341 };
342
343 struct quadd_module_version {
344         u8 branch[32];
345         u8 version[16];
346
347         u32 samples_version;
348         u32 io_version;
349
350         u32 reserved[4];        /* reserved fields for future extensions */
351 };
352
353 #pragma pack(pop)
354
355 #ifdef __KERNEL__
356
357 struct task_struct;
358 struct vm_area_struct;
359
360 #ifdef CONFIG_TEGRA_PROFILER
361 extern void __quadd_task_sched_in(struct task_struct *prev,
362                                   struct task_struct *task);
363 extern void __quadd_task_sched_out(struct task_struct *prev,
364                                    struct task_struct *next);
365
366 extern void __quadd_event_mmap(struct vm_area_struct *vma);
367
368 static inline void quadd_task_sched_in(struct task_struct *prev,
369                                        struct task_struct *task)
370 {
371         __quadd_task_sched_in(prev, task);
372 }
373
374 static inline void quadd_task_sched_out(struct task_struct *prev,
375                                         struct task_struct *next)
376 {
377         __quadd_task_sched_out(prev, next);
378 }
379
380 static inline void quadd_event_mmap(struct vm_area_struct *vma)
381 {
382         __quadd_event_mmap(vma);
383 }
384
385 #else   /* CONFIG_TEGRA_PROFILER */
386
387 static inline void quadd_task_sched_in(struct task_struct *prev,
388                                        struct task_struct *task)
389 {
390 }
391
392 static inline void quadd_task_sched_out(struct task_struct *prev,
393                                         struct task_struct *next)
394 {
395 }
396
397 static inline void quadd_event_mmap(struct vm_area_struct *vma)
398 {
399 }
400
401 #endif  /* CONFIG_TEGRA_PROFILER */
402
403 #endif  /* __KERNEL__ */
404
405 #endif  /* __TEGRA_PROFILER_H */