aboutsummaryrefslogtreecommitdiffstats
path: root/litmus/trace.c
diff options
context:
space:
mode:
Diffstat (limited to 'litmus/trace.c')
-rw-r--r--litmus/trace.c102
1 files changed, 102 insertions, 0 deletions
diff --git a/litmus/trace.c b/litmus/trace.c
new file mode 100644
index 000000000000..5735d28f5e30
--- /dev/null
+++ b/litmus/trace.c
@@ -0,0 +1,102 @@
1#include <linux/module.h>
2
3#include <litmus/ftdev.h>
4#include <litmus/litmus.h>
5#include <litmus/trace.h>
6
7/******************************************************************************/
8/* Allocation */
9/******************************************************************************/
10
11static struct ftdev overhead_dev;
12
13#define trace_ts_buf overhead_dev.minor[0].buf
14
15static unsigned int ts_seq_no = 0;
16
17static inline void __save_timestamp_cpu(unsigned long event,
18 uint8_t type, uint8_t cpu)
19{
20 unsigned int seq_no;
21 struct timestamp *ts;
22 seq_no = fetch_and_inc((int *) &ts_seq_no);
23 if (ft_buffer_start_write(trace_ts_buf, (void**) &ts)) {
24 ts->event = event;
25 ts->timestamp = ft_timestamp();
26 ts->seq_no = seq_no;
27 ts->cpu = cpu;
28 ts->task_type = type;
29 ft_buffer_finish_write(trace_ts_buf, ts);
30 }
31}
32
33static inline void __save_timestamp(unsigned long event,
34 uint8_t type)
35{
36 __save_timestamp_cpu(event, type, raw_smp_processor_id());
37}
38
39feather_callback void save_timestamp(unsigned long event)
40{
41 __save_timestamp(event, TSK_UNKNOWN);
42}
43
44feather_callback void save_timestamp_def(unsigned long event,
45 unsigned long type)
46{
47 __save_timestamp(event, (uint8_t) type);
48}
49
50feather_callback void save_timestamp_task(unsigned long event,
51 unsigned long t_ptr)
52{
53 int rt = is_realtime((struct task_struct *) t_ptr);
54 __save_timestamp(event, rt ? TSK_RT : TSK_BE);
55}
56
57feather_callback void save_timestamp_cpu(unsigned long event,
58 unsigned long cpu)
59{
60 __save_timestamp_cpu(event, TSK_UNKNOWN, cpu);
61}
62
63/******************************************************************************/
64/* DEVICE FILE DRIVER */
65/******************************************************************************/
66
67/*
68 * should be 8M; it is the max we can ask to buddy system allocator (MAX_ORDER)
69 * and we might not get as much
70 */
71#define NO_TIMESTAMPS (2 << 11)
72
73#define FT_TRACE_MAJOR 252
74
75static int alloc_timestamp_buffer(struct ftdev* ftdev, unsigned int idx)
76{
77 unsigned int count = NO_TIMESTAMPS;
78 while (count && !trace_ts_buf) {
79 printk("time stamp buffer: trying to allocate %u time stamps.\n", count);
80 ftdev->minor[idx].buf = alloc_ft_buffer(count, sizeof(struct timestamp));
81 count /= 2;
82 }
83 return ftdev->minor[idx].buf ? 0 : -ENOMEM;
84}
85
86static void free_timestamp_buffer(struct ftdev* ftdev, unsigned int idx)
87{
88 free_ft_buffer(ftdev->minor[idx].buf);
89 ftdev->minor[idx].buf = NULL;
90}
91
92static int __init init_ft_overhead_trace(void)
93{
94 printk("Initializing Feather-Trace overhead tracing device.\n");
95 ftdev_init(&overhead_dev, THIS_MODULE);
96 overhead_dev.minor_cnt = 1; /* only one buffer */
97 overhead_dev.alloc = alloc_timestamp_buffer;
98 overhead_dev.free = free_timestamp_buffer;
99 return register_ftdev(&overhead_dev, "ft_trace", FT_TRACE_MAJOR);
100}
101
102module_init(init_ft_overhead_trace);