1 #ifndef __PERF_CALLCHAIN_H
2 #define __PERF_CALLCHAIN_H
5 #include <linux/list.h>
6 #include <linux/rbtree.h>
22 struct callchain_node
{
23 struct callchain_node
*parent
;
24 struct list_head siblings
;
25 struct list_head children
;
27 struct rb_node rb_node
; /* to sort nodes in an rbtree */
28 struct rb_root rb_root
; /* sorted tree of children */
34 struct callchain_root
{
36 struct callchain_node node
;
39 struct callchain_param
;
41 typedef void (*sort_chain_func_t
)(struct rb_root
*, struct callchain_root
*,
42 u64
, struct callchain_param
*);
44 struct callchain_param
{
48 sort_chain_func_t sort
;
49 enum chain_order order
;
52 struct callchain_list
{
55 struct list_head list
;
59 * A callchain cursor is a single linked list that
60 * let one feed a callchain progressively.
61 * It keeps persitent allocated entries to minimize
64 struct callchain_cursor_node
{
68 struct callchain_cursor_node
*next
;
71 struct callchain_cursor
{
73 struct callchain_cursor_node
*first
;
74 struct callchain_cursor_node
**last
;
76 struct callchain_cursor_node
*curr
;
79 static inline void callchain_init(struct callchain_root
*root
)
81 INIT_LIST_HEAD(&root
->node
.siblings
);
82 INIT_LIST_HEAD(&root
->node
.children
);
83 INIT_LIST_HEAD(&root
->node
.val
);
85 root
->node
.parent
= NULL
;
87 root
->node
.children_hit
= 0;
91 static inline u64
callchain_cumul_hits(struct callchain_node
*node
)
93 return node
->hit
+ node
->children_hit
;
96 int callchain_register_param(struct callchain_param
*param
);
97 int callchain_append(struct callchain_root
*root
,
98 struct callchain_cursor
*cursor
,
101 int callchain_merge(struct callchain_cursor
*cursor
,
102 struct callchain_root
*dst
, struct callchain_root
*src
);
107 bool ip_callchain__valid(struct ip_callchain
*chain
,
108 const union perf_event
*event
);
110 * Initialize a cursor before adding entries inside, but keep
111 * the previously allocated entries as a cache.
113 static inline void callchain_cursor_reset(struct callchain_cursor
*cursor
)
116 cursor
->last
= &cursor
->first
;
119 int callchain_cursor_append(struct callchain_cursor
*cursor
, u64 ip
,
120 struct map
*map
, struct symbol
*sym
);
122 /* Close a cursor writing session. Initialize for the reader */
123 static inline void callchain_cursor_commit(struct callchain_cursor
*cursor
)
125 cursor
->curr
= cursor
->first
;
129 /* Cursor reading iteration helpers */
130 static inline struct callchain_cursor_node
*
131 callchain_cursor_current(struct callchain_cursor
*cursor
)
133 if (cursor
->pos
== cursor
->nr
)
139 static inline void callchain_cursor_advance(struct callchain_cursor
*cursor
)
141 cursor
->curr
= cursor
->curr
->next
;
144 #endif /* __PERF_CALLCHAIN_H */