prof: fixes backtrace
[akaros.git] / kern / src / oprofile / cpu_buffer.c
1 /**
2  * @file cpu_buffer.c
3  *
4  * @remark Copyright 2002-2009 OProfile authors
5  * @remark Read the file COPYING
6  *
7  * @author John Levon <levon@movementarian.org>
8  * @author Barry Kasindorf <barry.kasindorf@amd.com>
9  * @author Robert Richter <robert.richter@amd.com>
10  *
11  * Each CPU has a local buffer that stores PC value/event
12  * pairs. We also log context switches when we notice them.
13  * Eventually each CPU's buffer is processed into the global
14  * event buffer by sync_buffer().
15  *
16  * We use a local buffer for two reasons: an NMI or similar
17  * interrupt cannot synchronise, and high sampling rates
18  * would lead to catastrophic global synchronisation if
19  * a global buffer was used.
20  */
21 #include "event_buffer.h"
22 #include "cpu_buffer.h"
23 #include "buffer_sync.h"
24 #include "oprof.h"
25
26 #define OP_BUFFER_FLAGS 0
27
28 /* we allocate an array of these and set the pointer in pcpui */
29 struct oprofile_cpu_buffer *op_cpu_buffer;
30
31 /* this one queue is used by #K to get all events. */
32 static struct queue *opq;
33
34 /* this is run from core 0 for all cpu buffers. */
35 static void wq_sync_buffer(void);
36 unsigned long oprofile_cpu_buffer_size = 65536;
37 unsigned long oprofile_backtrace_depth = 8;
38
39 #define DEFAULT_TIMER_EXPIRE (HZ / 10)
40 static int work_enabled;
41
42 /*
43  * Resets the cpu buffer to a sane state.
44  *
45  * reset these to invalid values; the next sample collected will
46  * populate the buffer with proper values to initialize the buffer
47  */
48 static inline void op_cpu_buffer_reset(int cpu)
49 {
50         //print_func_entry();
51         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
52
53         cpu_buf->last_is_kernel = -1;
54         cpu_buf->last_proc = NULL;
55         //print_func_exit();
56 }
57
58 /* returns the remaining free size of data in the entry */
59 static inline
60         int op_cpu_buffer_add_data(struct op_entry *entry, unsigned long val)
61 {
62         //print_func_entry();
63         assert(entry->size >= 0);
64         if (!entry->size) {
65                 //print_func_exit();
66                 return 0;
67         }
68         *entry->data = val;
69         entry->size--;
70         entry->data++;
71         //print_func_exit();
72         return entry->size;
73 }
74
75 /* returns the size of data in the entry */
76 static inline int op_cpu_buffer_get_size(struct op_entry *entry)
77 {
78         //print_func_entry();
79         //print_func_exit();
80         return entry->size;
81 }
82
83 /* returns 0 if empty or the size of data including the current value */
84 static inline
85         int op_cpu_buffer_get_data(struct op_entry *entry, unsigned long *val)
86 {
87         //print_func_entry();
88         int size = entry->size;
89         if (!size) {
90                 //print_func_exit();
91                 return 0;
92         }
93         *val = *entry->data;
94         entry->size--;
95         entry->data++;
96         //print_func_exit();
97         return size;
98 }
99
100 unsigned long oprofile_get_cpu_buffer_size(void)
101 {
102         //print_func_entry();
103         //print_func_exit();
104         return oprofile_cpu_buffer_size;
105 }
106
107 void oprofile_cpu_buffer_inc_smpl_lost(void)
108 {
109         //print_func_entry();
110         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
111
112         cpu_buf->sample_lost_overflow++;
113         //print_func_exit();
114 }
115
116 void free_cpu_buffers(void)
117 {
118         //print_func_entry();
119         kfree(op_cpu_buffer);
120         /* we can just leave the queue set up; it will then always return EOF */
121         //print_func_exit();
122 }
123
124 #define RB_EVENT_HDR_SIZE 4
125
126 int alloc_cpu_buffers(void)
127 {
128         //print_func_entry();
129         /* should probably start using waserror() here. The fail stuff just gets
130          * ugly.
131          */
132         int i;
133         unsigned long buffer_size = oprofile_cpu_buffer_size;
134         unsigned long byte_size = buffer_size * (sizeof(struct op_sample) +
135                                                  RB_EVENT_HDR_SIZE);
136         /* this can get called lots of times. Things might have been freed.
137          * So be careful.
138          */
139         /* what limit? No idea. */
140         if (!opq)
141                 opq = qopen(1024, 0, NULL, NULL);
142         if (!opq)
143                 goto fail;
144
145         /* we *really* don't want to block. Losing data is better. */
146         qnoblock(opq, 1);
147         if (!op_cpu_buffer) {
148                 printk("ALlocate %d bytes\n", sizeof(*op_cpu_buffer) * num_cpus);
149                 op_cpu_buffer =
150                         kzmalloc(sizeof(*op_cpu_buffer) * num_cpus, KMALLOC_WAIT);
151                 if (!op_cpu_buffer)
152                         goto fail;
153
154                 for (i = 0; i < num_cpus; i++) {
155                         struct oprofile_cpu_buffer *b = &op_cpu_buffer[i];
156                         b->last_proc = NULL;
157                         b->last_is_kernel = -1;
158                         b->tracing = 0;
159                         b->buffer_size = buffer_size;
160                         b->sample_received = 0;
161                         b->sample_lost_overflow = 0;
162                         b->backtrace_aborted = 0;
163                         b->sample_invalid_eip = 0;
164                         b->cpu = i;
165                         b->fullqueue = qopen(1024, Qmsg, NULL, NULL);
166                         b->emptyqueue = qopen(1024, Qmsg, NULL, NULL);
167                         spinlock_init_irqsave(&b->lock);
168                 }
169         }
170
171         //print_func_exit();
172         return 0;
173
174 fail:
175         free_cpu_buffers();
176         //print_func_exit();
177         return -ENOMEM;
178 }
179
180 void start_cpu_work(void)
181 {
182         //print_func_entry();
183         int i;
184
185         work_enabled = 1;
186         /* task starts here.
187            schedule_delayed_work_on(i, &b->work, DEFAULT_TIMER_EXPIRE + i);
188          */
189         //print_func_exit();
190 }
191
192 void end_cpu_work(void)
193 {
194         //print_func_entry();
195         work_enabled = 0;
196         //print_func_exit();
197 }
198
199 /* placeholder. Not used yet.
200  */
201 void flush_cpu_work(void)
202 {
203         //print_func_entry();
204         int i;
205         struct oprofile_cpu_buffer *b = &op_cpu_buffer[core_id()];
206
207         //print_func_exit();
208 }
209
210 /* Not used since we're not doing per-cpu buffering yet.
211  */
212
213 struct op_sample *op_cpu_buffer_read_entry(struct op_entry *entry, int cpu)
214 {
215         //print_func_entry();
216         //print_func_exit();
217         return NULL;
218 }
219
220 static struct block *op_cpu_buffer_write_reserve(struct oprofile_cpu_buffer *cpu_buf,
221         struct op_entry *entry, int size)
222 {
223         //print_func_entry();
224         struct block *b;
225         int totalsize = sizeof(struct op_sample) +
226                 size * sizeof(entry->sample->data[0]);
227
228         b = cpu_buf->block;
229         /* we might have run out. */
230         if ((! b) || (b->lim - b->wp) < size) {
231                 if (b){
232                         qibwrite(opq, b);
233                 }
234                 /* For now. Later, we will grab a block off the
235                  * emptyblock queue.
236                  */
237                 cpu_buf->block = b = iallocb(oprofile_cpu_buffer_size);
238                 if (!b) {
239                         printk("%s: fail\n", __func__);
240                         //print_func_exit();
241                         return NULL;
242                 }
243         }
244         entry->sample = (void *)b->wp;
245         entry->size = size;
246         entry->data = entry->sample->data;
247
248         b->wp += totalsize;
249         //print_func_exit();
250         return b;
251
252 }
253
254 static int
255 op_add_code(struct oprofile_cpu_buffer *cpu_buf, unsigned long backtrace,
256                         int is_kernel, struct proc *proc)
257 {
258         //print_func_entry();
259         struct block *b;
260         struct op_entry entry;
261         struct op_sample *sample;
262         unsigned long flags;
263         int size;
264         ERRSTACK(1);
265
266         flags = 0;
267
268         if (waserror()) {
269                 poperror();
270                 printk("%s: failed\n", __func__);
271                 //print_func_exit();
272                 return 1;
273         }
274
275         if (backtrace)
276                 flags |= TRACE_BEGIN;
277
278         /* notice a switch from user->kernel or vice versa */
279         is_kernel = ! !is_kernel;
280         if (cpu_buf->last_is_kernel != is_kernel) {
281                 cpu_buf->last_is_kernel = is_kernel;
282                 flags |= KERNEL_CTX_SWITCH;
283                 if (is_kernel)
284                         flags |= IS_KERNEL;
285         }
286
287         /* notice a proc switch */
288         if (cpu_buf->last_proc != proc) {
289                 cpu_buf->last_proc = proc;
290                 flags |= USER_CTX_SWITCH;
291         }
292
293         if (!flags) {
294                 poperror();
295                 /* nothing to do */
296                 //print_func_exit();
297                 return 0;
298         }
299
300         if (flags & USER_CTX_SWITCH)
301                 size = 1;
302         else
303                 size = 0;
304
305         b = op_cpu_buffer_write_reserve(cpu_buf, &entry, size);
306
307         entry.sample->eip = ESCAPE_CODE;
308         entry.sample->event = flags;
309
310         if (size)
311                 op_cpu_buffer_add_data(&entry, (unsigned long)proc);
312
313         poperror();
314         //print_func_exit();
315         return 0;
316 }
317
318 static inline int
319 op_add_sample(struct oprofile_cpu_buffer *cpu_buf,
320                           unsigned long pc, unsigned long event)
321 {
322         //print_func_entry();
323         ERRSTACK(1);
324         struct op_entry entry;
325         struct op_sample *sample;
326         struct block *b;
327
328         if (waserror()) {
329                 poperror();
330                 printk("%s: failed\n", __func__);
331                 //print_func_exit();
332                 return 1;
333         }
334
335         b = op_cpu_buffer_write_reserve(cpu_buf, &entry, 0);
336
337         sample = entry.sample;
338         sample->eip = pc;
339         sample->event = event;
340         poperror();
341         //print_func_exit();
342         return 0;
343 }
344
345 /*
346  * This must be safe from any context.
347  *
348  * is_kernel is needed because on some architectures you cannot
349  * tell if you are in kernel or user space simply by looking at
350  * pc. We tag this in the buffer by generating kernel enter/exit
351  * events whenever is_kernel changes
352  */
353 static int
354 log_sample(struct oprofile_cpu_buffer *cpu_buf, unsigned long pc,
355                    unsigned long backtrace, int is_kernel, unsigned long event,
356                    struct proc *proc)
357 {
358         //print_func_entry();
359         struct proc *tsk = proc ? proc : current;
360         cpu_buf->sample_received++;
361
362         if (pc == ESCAPE_CODE) {
363                 cpu_buf->sample_invalid_eip++;
364                 //print_func_exit();
365                 return 0;
366         }
367
368         /* ah, so great. op_add* return 1 in event of failure.
369          * this function returns 0 in event of failure.
370          * what a cluster.
371          */
372         spin_lock_irqsave(&cpu_buf->lock);
373         if (op_add_code(cpu_buf, backtrace, is_kernel, tsk))
374                 goto fail;
375
376         if (op_add_sample(cpu_buf, pc, event))
377                 goto fail;
378         spin_unlock_irqsave(&cpu_buf->lock);
379
380         //print_func_exit();
381         return 1;
382
383 fail:
384         cpu_buf->sample_lost_overflow++;
385         //print_func_exit();
386         return 0;
387 }
388
389 static inline void oprofile_begin_trace(struct oprofile_cpu_buffer *cpu_buf)
390 {
391         //print_func_entry();
392         cpu_buf->tracing = 1;
393         //print_func_exit();
394 }
395
396 static inline void oprofile_end_trace(struct oprofile_cpu_buffer *cpu_buf)
397 {
398         //print_func_entry();
399         cpu_buf->tracing = 0;
400         //print_func_exit();
401 }
402
403 void oprofile_cpubuf_flushone(int core, int newbuf)
404 {
405         //print_func_entry();
406         struct oprofile_cpu_buffer *cpu_buf;
407         cpu_buf = &op_cpu_buffer[core];
408         spin_lock_irqsave(&cpu_buf->lock);
409         if (cpu_buf->block) {
410                 printk("Core %d has data\n", core);
411                 qibwrite(opq, cpu_buf->block);
412                 printk("After qibwrite in %s, opq len %d\n", __func__, qlen(opq));
413         }
414         if (newbuf)
415                 cpu_buf->block = iallocb(oprofile_cpu_buffer_size);
416         else
417                 cpu_buf->block = NULL;
418         spin_unlock_irqsave(&cpu_buf->lock);
419         //print_func_exit();
420 }
421
422 void oprofile_cpubuf_flushall(int alloc)
423 {
424         //print_func_entry();
425         int core;
426
427         for(core = 0; core < num_cpus; core++) {
428                 oprofile_cpubuf_flushone(core, alloc);
429         }
430         //print_func_exit();
431 }
432
433 void oprofile_control_trace(int onoff)
434 {
435         //print_func_entry();
436         int core;
437         struct oprofile_cpu_buffer *cpu_buf;
438
439         for(core = 0; core < num_cpus; core++) {
440                 cpu_buf = &op_cpu_buffer[core];
441                 cpu_buf->tracing = onoff;
442
443                 if (onoff) {
444                         printk("Enable tracing on %d\n", core);
445                         continue;
446                 }
447
448                 /* halting. Force out all buffers. */
449                 oprofile_cpubuf_flushone(core, 0);
450         }
451         //print_func_exit();
452 }
453
454 static inline void
455 __oprofile_add_ext_sample(unsigned long pc,
456                                                   void /*struct pt_regs */ *const regs,
457                                                   unsigned long event, int is_kernel, struct proc *proc)
458 {
459         //print_func_entry();
460         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
461         unsigned long backtrace = oprofile_backtrace_depth;
462
463         /*
464          * if log_sample() fail we can't backtrace since we lost the
465          * source of this event
466          */
467         if (!log_sample(cpu_buf, pc, backtrace, is_kernel, event, proc))
468                 /* failed */
469         {
470                 //print_func_exit();
471                 return;
472         }
473
474         if (!backtrace) {
475                 //print_func_exit();
476                 return;
477         }
478 #if 0
479         oprofile_begin_trace(cpu_buf);
480         oprofile_ops.backtrace(regs, backtrace);
481         oprofile_end_trace(cpu_buf);
482 #endif
483         //print_func_exit();
484 }
485
486 void oprofile_add_ext_hw_sample(unsigned long pc,
487                                                                 void /*struct pt_regs */ *const regs,
488                                                                 unsigned long event, int is_kernel,
489                                                                 struct proc *proc)
490 {
491         //print_func_entry();
492         __oprofile_add_ext_sample(pc, regs, event, is_kernel, proc);
493         //print_func_exit();
494 }
495
496 void oprofile_add_ext_sample(unsigned long pc,
497                                                          void /*struct pt_regs */ *const regs,
498                                                          unsigned long event, int is_kernel)
499 {
500         //print_func_entry();
501         __oprofile_add_ext_sample(pc, regs, event, is_kernel, NULL);
502         //print_func_exit();
503 }
504
505 void oprofile_add_sample(void /*struct pt_regs */ *const regs,
506                                                  unsigned long event)
507 {
508         //print_func_entry();
509         int is_kernel;
510         unsigned long pc;
511
512         if (regs) {
513                 is_kernel = 0;  // FIXME!user_mode(regs);
514                 pc = 0; // FIXME profile_pc(regs);
515         } else {
516                 is_kernel = 0;  /* This value will not be used */
517                 pc = ESCAPE_CODE;       /* as this causes an early return. */
518         }
519
520         __oprofile_add_ext_sample(pc, regs, event, is_kernel, NULL);
521         //print_func_exit();
522 }
523
524 /*
525  * Add samples with data to the ring buffer.
526  *
527  * Use oprofile_add_data(&entry, val) to add data and
528  * oprofile_write_commit(&entry) to commit the sample.
529  */
530 void
531 oprofile_write_reserve(struct op_entry *entry,
532                                            void /*struct pt_regs */ *const regs,
533                                            unsigned long pc, int code, int size)
534 {
535         //print_func_entry();
536         ERRSTACK(1);
537         struct op_sample *sample;
538         struct block *b;
539         int is_kernel = 0;                      // FIXME!user_mode(regs);
540         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
541
542         if (waserror()) {
543                 printk("%s: failed\n", __func__);
544                 poperror();
545                 goto fail;
546         }
547         cpu_buf->sample_received++;
548
549         /* no backtraces for samples with data */
550         if (op_add_code(cpu_buf, 0, is_kernel, current))
551                 goto fail;
552
553         b = op_cpu_buffer_write_reserve(cpu_buf, entry, size + 2);
554         sample = entry->sample;
555         sample->eip = ESCAPE_CODE;
556         sample->event = 0;      /* no flags */
557
558         op_cpu_buffer_add_data(entry, code);
559         op_cpu_buffer_add_data(entry, pc);
560         poperror();
561         //print_func_exit();
562         return;
563 fail:
564         entry->event = NULL;
565         cpu_buf->sample_lost_overflow++;
566         //print_func_exit();
567 }
568
569 int oprofile_add_data(struct op_entry *entry, unsigned long val)
570 {
571         //print_func_entry();
572         if (!entry->event) {
573                 //print_func_exit();
574                 return 0;
575         }
576         //print_func_exit();
577         return op_cpu_buffer_add_data(entry, val);
578 }
579
580 int oprofile_add_data64(struct op_entry *entry, uint64_t val)
581 {
582         //print_func_entry();
583         if (!entry->event) {
584                 //print_func_exit();
585                 return 0;
586         }
587         if (op_cpu_buffer_get_size(entry) < 2)
588                 /*
589                  * the function returns 0 to indicate a too small
590                  * buffer, even if there is some space left
591                  */
592         {
593                 //print_func_exit();
594                 return 0;
595         }
596         if (!op_cpu_buffer_add_data(entry, (uint32_t) val)) {
597                 //print_func_exit();
598                 return 0;
599         }
600         //print_func_exit();
601         return op_cpu_buffer_add_data(entry, (uint32_t) (val >> 32));
602 }
603
604 int oprofile_write_commit(struct op_entry *entry)
605 {
606         //print_func_entry();
607         /* not much to do at present. In future, we might write the Block
608          * to opq.
609          */
610         //print_func_exit();
611         return 0;
612 }
613
614 void oprofile_add_pc(unsigned long pc, int is_kernel, unsigned long event)
615 {
616         //print_func_entry();
617         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
618         log_sample(cpu_buf, pc, 0, is_kernel, event, NULL);
619         //print_func_exit();
620 }
621
622 void oprofile_add_trace(unsigned long pc)
623 {
624         if (! op_cpu_buffer)
625                 return;
626         //print_func_entry();
627         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
628
629         if (!cpu_buf->tracing) {
630                 //print_func_exit();
631                 return;
632         }
633
634         /*
635          * broken frame can give an eip with the same value as an
636          * escape code, abort the trace if we get it
637          */
638         if (pc == ESCAPE_CODE)
639                 goto fail;
640         if (op_add_sample(cpu_buf, pc, nsec()&~0xf))
641                 goto fail;
642
643         //print_func_exit();
644         return;
645 fail:
646         printk("%s: fail. Turning of tracing on cpu %d\n", core_id());
647         cpu_buf->tracing = 0;
648         cpu_buf->backtrace_aborted++;
649         //print_func_exit();
650         return;
651 }
652
653 /* Format for samples:
654  * first word:
655  * high 8 bits is ee, which is an invalid address on amd64. 
656  * next 8 bits is protocol version
657  * next 16 bits is unused, MBZ. Later, we can make it a packet type. 
658  * next 16 bits is core id
659  * next 8 bits is unused
660  * next 8 bits is # PCs following. This should be at least 1, for one EIP.
661  *
662  * second word is time in ns.
663  * 
664  * Third and following words are PCs, there must be at least one of them. 
665  */
666 void oprofile_add_backtrace(uintptr_t ebp)
667 {
668         /* version 1. */
669         uint64_t descriptor = 0xee01ULL<<48;
670         if (! op_cpu_buffer)
671                 return;
672         //print_func_entry();
673         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
674
675         if (!cpu_buf->tracing) {
676                 //print_func_exit();
677                 return;
678         }
679
680         uintptr_t eip = get_caller_pc();
681
682         struct op_entry entry;
683         struct op_sample *sample;
684         struct block *b;
685         uint64_t event = nsec();
686
687         uintptr_t bt_pcs[oprofile_backtrace_depth];
688         
689         int nr_pcs;
690         nr_pcs = backtrace_list(eip, ebp, bt_pcs, oprofile_backtrace_depth);
691
692         /* write_reserve always assumes passed-in-size + 2.
693          * backtrace_depth should always be > 0.
694          */
695         b = op_cpu_buffer_write_reserve(cpu_buf, &entry, nr_pcs);
696
697         if (! b)
698                 return;
699
700         /* we are changing the sample format, but not the struct
701          * member names yet. Later, assuming this works out.
702          */
703         descriptor |= (core_id() << 16) | nr_pcs;
704         sample = entry.sample;
705         sample->eip = descriptor;
706         sample->event = event;
707         memcpy(sample->data, bt_pcs, sizeof(uintptr_t) * nr_pcs);
708
709         //print_func_exit();
710         return;
711 fail:
712         printk("%s: fail. Turning of tracing on cpu %d\n", core_id());
713         cpu_buf->tracing = 0;
714         cpu_buf->backtrace_aborted++;
715         //print_func_exit();
716         return;
717 }
718
719 int
720 oproflen(void)
721 {
722         return qlen(opq);
723 }
724
725 /* return # bytes read, or 0 if profiling is off, or block if profiling on and no data.
726  */
727 int
728 oprofread(void *va, int n)
729 {
730         int len = qlen(opq);
731         struct oprofile_cpu_buffer *cpu_buf = &op_cpu_buffer[core_id()];
732         if (len == 0) {
733                 if (cpu_buf->tracing == 0)
734                         return 0;
735         }
736
737         len = qread(opq, va, n);
738         return len;
739 }