2 * Copyright (C) 2009, 2010 Red Hat Inc, Steven Rostedt <srostedt@redhat.com>
4 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation;
8 * version 2.1 of the License (not later!)
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU Lesser General Public License for more details.
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this program; if not, see <http://www.gnu.org/licenses>
18 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
20 * The parts for function graph printing was taken and modified from the
21 * Linux Kernel that were written by
22 * - Copyright (C) 2009 Frederic Weisbecker,
23 * Frederic Weisbecker gave his permission to relicense the code to
24 * the Lesser General Public License.
35 #include "event-parse.h"
36 #include "event-utils.h"
38 static const char *input_buf
;
39 static unsigned long long input_buf_ptr
;
40 static unsigned long long input_buf_siz
;
42 static int is_flag_field
;
43 static int is_symbolic_field
;
45 static int show_warning
= 1;
47 #define do_warning(fmt, ...) \
50 warning(fmt, ##__VA_ARGS__); \
53 #define do_warning_event(event, fmt, ...) \
59 warning("[%s:%s] " fmt, event->system, \
60 event->name, ##__VA_ARGS__); \
62 warning(fmt, ##__VA_ARGS__); \
65 static void init_input_buf(const char *buf
, unsigned long long size
)
72 const char *pevent_get_input_buf(void)
77 unsigned long long pevent_get_input_buf_ptr(void)
82 struct event_handler
{
83 struct event_handler
*next
;
86 const char *event_name
;
87 pevent_event_handler_func func
;
91 struct pevent_func_params
{
92 struct pevent_func_params
*next
;
93 enum pevent_func_arg_type type
;
96 struct pevent_function_handler
{
97 struct pevent_function_handler
*next
;
98 enum pevent_func_arg_type ret_type
;
100 pevent_func_handler func
;
101 struct pevent_func_params
*params
;
105 static unsigned long long
106 process_defined_func(struct trace_seq
*s
, void *data
, int size
,
107 struct event_format
*event
, struct print_arg
*arg
);
109 static void free_func_handle(struct pevent_function_handler
*func
);
112 * pevent_buffer_init - init buffer for parsing
113 * @buf: buffer to parse
114 * @size: the size of the buffer
116 * For use with pevent_read_token(), this initializes the internal
117 * buffer that pevent_read_token() will parse.
119 void pevent_buffer_init(const char *buf
, unsigned long long size
)
121 init_input_buf(buf
, size
);
124 void breakpoint(void)
130 struct print_arg
*alloc_arg(void)
132 return calloc(1, sizeof(struct print_arg
));
140 static int cmdline_cmp(const void *a
, const void *b
)
142 const struct cmdline
*ca
= a
;
143 const struct cmdline
*cb
= b
;
145 if (ca
->pid
< cb
->pid
)
147 if (ca
->pid
> cb
->pid
)
153 struct cmdline_list
{
154 struct cmdline_list
*next
;
159 static int cmdline_init(struct pevent
*pevent
)
161 struct cmdline_list
*cmdlist
= pevent
->cmdlist
;
162 struct cmdline_list
*item
;
163 struct cmdline
*cmdlines
;
166 cmdlines
= malloc(sizeof(*cmdlines
) * pevent
->cmdline_count
);
172 cmdlines
[i
].pid
= cmdlist
->pid
;
173 cmdlines
[i
].comm
= cmdlist
->comm
;
176 cmdlist
= cmdlist
->next
;
180 qsort(cmdlines
, pevent
->cmdline_count
, sizeof(*cmdlines
), cmdline_cmp
);
182 pevent
->cmdlines
= cmdlines
;
183 pevent
->cmdlist
= NULL
;
188 static const char *find_cmdline(struct pevent
*pevent
, int pid
)
190 const struct cmdline
*comm
;
196 if (!pevent
->cmdlines
&& cmdline_init(pevent
))
197 return "<not enough memory for cmdlines!>";
201 comm
= bsearch(&key
, pevent
->cmdlines
, pevent
->cmdline_count
,
202 sizeof(*pevent
->cmdlines
), cmdline_cmp
);
210 * pevent_pid_is_registered - return if a pid has a cmdline registered
211 * @pevent: handle for the pevent
212 * @pid: The pid to check if it has a cmdline registered with.
214 * Returns 1 if the pid has a cmdline mapped to it
217 int pevent_pid_is_registered(struct pevent
*pevent
, int pid
)
219 const struct cmdline
*comm
;
225 if (!pevent
->cmdlines
&& cmdline_init(pevent
))
230 comm
= bsearch(&key
, pevent
->cmdlines
, pevent
->cmdline_count
,
231 sizeof(*pevent
->cmdlines
), cmdline_cmp
);
239 * If the command lines have been converted to an array, then
240 * we must add this pid. This is much slower than when cmdlines
241 * are added before the array is initialized.
243 static int add_new_comm(struct pevent
*pevent
, const char *comm
, int pid
)
245 struct cmdline
*cmdlines
= pevent
->cmdlines
;
246 const struct cmdline
*cmdline
;
252 /* avoid duplicates */
255 cmdline
= bsearch(&key
, pevent
->cmdlines
, pevent
->cmdline_count
,
256 sizeof(*pevent
->cmdlines
), cmdline_cmp
);
262 cmdlines
= realloc(cmdlines
, sizeof(*cmdlines
) * (pevent
->cmdline_count
+ 1));
268 cmdlines
[pevent
->cmdline_count
].comm
= strdup(comm
);
269 if (!cmdlines
[pevent
->cmdline_count
].comm
) {
275 cmdlines
[pevent
->cmdline_count
].pid
= pid
;
277 if (cmdlines
[pevent
->cmdline_count
].comm
)
278 pevent
->cmdline_count
++;
280 qsort(cmdlines
, pevent
->cmdline_count
, sizeof(*cmdlines
), cmdline_cmp
);
281 pevent
->cmdlines
= cmdlines
;
287 * pevent_register_comm - register a pid / comm mapping
288 * @pevent: handle for the pevent
289 * @comm: the command line to register
290 * @pid: the pid to map the command line to
292 * This adds a mapping to search for command line names with
293 * a given pid. The comm is duplicated.
295 int pevent_register_comm(struct pevent
*pevent
, const char *comm
, int pid
)
297 struct cmdline_list
*item
;
299 if (pevent
->cmdlines
)
300 return add_new_comm(pevent
, comm
, pid
);
302 item
= malloc(sizeof(*item
));
306 item
->comm
= strdup(comm
);
312 item
->next
= pevent
->cmdlist
;
314 pevent
->cmdlist
= item
;
315 pevent
->cmdline_count
++;
320 void pevent_register_trace_clock(struct pevent
*pevent
, char *trace_clock
)
322 pevent
->trace_clock
= trace_clock
;
326 unsigned long long addr
;
332 struct func_list
*next
;
333 unsigned long long addr
;
338 static int func_cmp(const void *a
, const void *b
)
340 const struct func_map
*fa
= a
;
341 const struct func_map
*fb
= b
;
343 if (fa
->addr
< fb
->addr
)
345 if (fa
->addr
> fb
->addr
)
352 * We are searching for a record in between, not an exact
355 static int func_bcmp(const void *a
, const void *b
)
357 const struct func_map
*fa
= a
;
358 const struct func_map
*fb
= b
;
360 if ((fa
->addr
== fb
->addr
) ||
362 (fa
->addr
> fb
->addr
&&
363 fa
->addr
< (fb
+1)->addr
))
366 if (fa
->addr
< fb
->addr
)
372 static int func_map_init(struct pevent
*pevent
)
374 struct func_list
*funclist
;
375 struct func_list
*item
;
376 struct func_map
*func_map
;
379 func_map
= malloc(sizeof(*func_map
) * (pevent
->func_count
+ 1));
383 funclist
= pevent
->funclist
;
387 func_map
[i
].func
= funclist
->func
;
388 func_map
[i
].addr
= funclist
->addr
;
389 func_map
[i
].mod
= funclist
->mod
;
392 funclist
= funclist
->next
;
396 qsort(func_map
, pevent
->func_count
, sizeof(*func_map
), func_cmp
);
399 * Add a special record at the end.
401 func_map
[pevent
->func_count
].func
= NULL
;
402 func_map
[pevent
->func_count
].addr
= 0;
403 func_map
[pevent
->func_count
].mod
= NULL
;
405 pevent
->func_map
= func_map
;
406 pevent
->funclist
= NULL
;
411 static struct func_map
*
412 find_func(struct pevent
*pevent
, unsigned long long addr
)
414 struct func_map
*func
;
417 if (!pevent
->func_map
)
418 func_map_init(pevent
);
422 func
= bsearch(&key
, pevent
->func_map
, pevent
->func_count
,
423 sizeof(*pevent
->func_map
), func_bcmp
);
429 * pevent_find_function - find a function by a given address
430 * @pevent: handle for the pevent
431 * @addr: the address to find the function with
433 * Returns a pointer to the function stored that has the given
434 * address. Note, the address does not have to be exact, it
435 * will select the function that would contain the address.
437 const char *pevent_find_function(struct pevent
*pevent
, unsigned long long addr
)
439 struct func_map
*map
;
441 map
= find_func(pevent
, addr
);
449 * pevent_find_function_address - find a function address by a given address
450 * @pevent: handle for the pevent
451 * @addr: the address to find the function with
453 * Returns the address the function starts at. This can be used in
454 * conjunction with pevent_find_function to print both the function
455 * name and the function offset.
458 pevent_find_function_address(struct pevent
*pevent
, unsigned long long addr
)
460 struct func_map
*map
;
462 map
= find_func(pevent
, addr
);
470 * pevent_register_function - register a function with a given address
471 * @pevent: handle for the pevent
472 * @function: the function name to register
473 * @addr: the address the function starts at
474 * @mod: the kernel module the function may be in (NULL for none)
476 * This registers a function name with an address and module.
477 * The @func passed in is duplicated.
479 int pevent_register_function(struct pevent
*pevent
, char *func
,
480 unsigned long long addr
, char *mod
)
482 struct func_list
*item
= malloc(sizeof(*item
));
487 item
->next
= pevent
->funclist
;
488 item
->func
= strdup(func
);
493 item
->mod
= strdup(mod
);
500 pevent
->funclist
= item
;
501 pevent
->func_count
++;
515 * pevent_print_funcs - print out the stored functions
516 * @pevent: handle for the pevent
518 * This prints out the stored functions.
520 void pevent_print_funcs(struct pevent
*pevent
)
524 if (!pevent
->func_map
)
525 func_map_init(pevent
);
527 for (i
= 0; i
< (int)pevent
->func_count
; i
++) {
529 pevent
->func_map
[i
].addr
,
530 pevent
->func_map
[i
].func
);
531 if (pevent
->func_map
[i
].mod
)
532 printf(" [%s]\n", pevent
->func_map
[i
].mod
);
539 unsigned long long addr
;
544 struct printk_list
*next
;
545 unsigned long long addr
;
549 static int printk_cmp(const void *a
, const void *b
)
551 const struct printk_map
*pa
= a
;
552 const struct printk_map
*pb
= b
;
554 if (pa
->addr
< pb
->addr
)
556 if (pa
->addr
> pb
->addr
)
562 static int printk_map_init(struct pevent
*pevent
)
564 struct printk_list
*printklist
;
565 struct printk_list
*item
;
566 struct printk_map
*printk_map
;
569 printk_map
= malloc(sizeof(*printk_map
) * (pevent
->printk_count
+ 1));
573 printklist
= pevent
->printklist
;
577 printk_map
[i
].printk
= printklist
->printk
;
578 printk_map
[i
].addr
= printklist
->addr
;
581 printklist
= printklist
->next
;
585 qsort(printk_map
, pevent
->printk_count
, sizeof(*printk_map
), printk_cmp
);
587 pevent
->printk_map
= printk_map
;
588 pevent
->printklist
= NULL
;
593 static struct printk_map
*
594 find_printk(struct pevent
*pevent
, unsigned long long addr
)
596 struct printk_map
*printk
;
597 struct printk_map key
;
599 if (!pevent
->printk_map
&& printk_map_init(pevent
))
604 printk
= bsearch(&key
, pevent
->printk_map
, pevent
->printk_count
,
605 sizeof(*pevent
->printk_map
), printk_cmp
);
611 * pevent_register_print_string - register a string by its address
612 * @pevent: handle for the pevent
613 * @fmt: the string format to register
614 * @addr: the address the string was located at
616 * This registers a string by the address it was stored in the kernel.
617 * The @fmt passed in is duplicated.
619 int pevent_register_print_string(struct pevent
*pevent
, const char *fmt
,
620 unsigned long long addr
)
622 struct printk_list
*item
= malloc(sizeof(*item
));
628 item
->next
= pevent
->printklist
;
631 /* Strip off quotes and '\n' from the end */
634 item
->printk
= strdup(fmt
);
638 p
= item
->printk
+ strlen(item
->printk
) - 1;
643 if (strcmp(p
, "\\n") == 0)
646 pevent
->printklist
= item
;
647 pevent
->printk_count
++;
658 * pevent_print_printk - print out the stored strings
659 * @pevent: handle for the pevent
661 * This prints the string formats that were stored.
663 void pevent_print_printk(struct pevent
*pevent
)
667 if (!pevent
->printk_map
)
668 printk_map_init(pevent
);
670 for (i
= 0; i
< (int)pevent
->printk_count
; i
++) {
671 printf("%016llx %s\n",
672 pevent
->printk_map
[i
].addr
,
673 pevent
->printk_map
[i
].printk
);
677 static struct event_format
*alloc_event(void)
679 return calloc(1, sizeof(struct event_format
));
682 static int add_event(struct pevent
*pevent
, struct event_format
*event
)
685 struct event_format
**events
= realloc(pevent
->events
, sizeof(event
) *
686 (pevent
->nr_events
+ 1));
690 pevent
->events
= events
;
692 for (i
= 0; i
< pevent
->nr_events
; i
++) {
693 if (pevent
->events
[i
]->id
> event
->id
)
696 if (i
< pevent
->nr_events
)
697 memmove(&pevent
->events
[i
+ 1],
699 sizeof(event
) * (pevent
->nr_events
- i
));
701 pevent
->events
[i
] = event
;
704 event
->pevent
= pevent
;
709 static int event_item_type(enum event_type type
)
712 case EVENT_ITEM
... EVENT_SQUOTE
:
714 case EVENT_ERROR
... EVENT_DELIM
:
720 static void free_flag_sym(struct print_flag_sym
*fsym
)
722 struct print_flag_sym
*next
;
733 static void free_arg(struct print_arg
*arg
)
735 struct print_arg
*farg
;
742 free(arg
->atom
.atom
);
745 free(arg
->field
.name
);
748 free_arg(arg
->flags
.field
);
749 free(arg
->flags
.delim
);
750 free_flag_sym(arg
->flags
.flags
);
753 free_arg(arg
->symbol
.field
);
754 free_flag_sym(arg
->symbol
.symbols
);
757 free_arg(arg
->hex
.field
);
758 free_arg(arg
->hex
.size
);
761 free(arg
->typecast
.type
);
762 free_arg(arg
->typecast
.item
);
766 free(arg
->string
.string
);
769 free(arg
->bitmask
.bitmask
);
771 case PRINT_DYNAMIC_ARRAY
:
772 free(arg
->dynarray
.index
);
776 free_arg(arg
->op
.left
);
777 free_arg(arg
->op
.right
);
780 while (arg
->func
.args
) {
781 farg
= arg
->func
.args
;
782 arg
->func
.args
= farg
->next
;
795 static enum event_type
get_type(int ch
)
798 return EVENT_NEWLINE
;
801 if (isalnum(ch
) || ch
== '_')
809 if (ch
== '(' || ch
== ')' || ch
== ',')
815 static int __read_char(void)
817 if (input_buf_ptr
>= input_buf_siz
)
820 return input_buf
[input_buf_ptr
++];
823 static int __peek_char(void)
825 if (input_buf_ptr
>= input_buf_siz
)
828 return input_buf
[input_buf_ptr
];
832 * pevent_peek_char - peek at the next character that will be read
834 * Returns the next character read, or -1 if end of buffer.
836 int pevent_peek_char(void)
838 return __peek_char();
841 static int extend_token(char **tok
, char *buf
, int size
)
843 char *newtok
= realloc(*tok
, size
);
860 static enum event_type
force_token(const char *str
, char **tok
);
862 static enum event_type
__read_token(char **tok
)
865 int ch
, last_ch
, quote_ch
, next_ch
;
868 enum event_type type
;
878 if (type
== EVENT_NONE
)
886 if (asprintf(tok
, "%c", ch
) < 0)
894 next_ch
= __peek_char();
895 if (next_ch
== '>') {
896 buf
[i
++] = __read_char();
909 buf
[i
++] = __read_char();
921 default: /* what should we do instead? */
931 buf
[i
++] = __read_char();
936 /* don't keep quotes */
942 if (i
== (BUFSIZ
- 1)) {
946 if (extend_token(tok
, buf
, tok_size
) < 0)
953 /* the '\' '\' will cancel itself */
954 if (ch
== '\\' && last_ch
== '\\')
956 } while (ch
!= quote_ch
|| last_ch
== '\\');
957 /* remove the last quote */
961 * For strings (double quotes) check the next token.
962 * If it is another string, concatinate the two.
964 if (type
== EVENT_DQUOTE
) {
965 unsigned long long save_input_buf_ptr
= input_buf_ptr
;
969 } while (isspace(ch
));
972 input_buf_ptr
= save_input_buf_ptr
;
977 case EVENT_ERROR
... EVENT_SPACE
:
983 while (get_type(__peek_char()) == type
) {
984 if (i
== (BUFSIZ
- 1)) {
988 if (extend_token(tok
, buf
, tok_size
) < 0)
998 if (extend_token(tok
, buf
, tok_size
+ i
+ 1) < 0)
1001 if (type
== EVENT_ITEM
) {
1003 * Older versions of the kernel has a bug that
1004 * creates invalid symbols and will break the mac80211
1005 * parsing. This is a work around to that bug.
1007 * See Linux kernel commit:
1008 * 811cb50baf63461ce0bdb234927046131fc7fa8b
1010 if (strcmp(*tok
, "LOCAL_PR_FMT") == 0) {
1013 return force_token("\"\%s\" ", tok
);
1014 } else if (strcmp(*tok
, "STA_PR_FMT") == 0) {
1017 return force_token("\" sta:%pM\" ", tok
);
1018 } else if (strcmp(*tok
, "VIF_PR_FMT") == 0) {
1021 return force_token("\" vif:%p(%d)\" ", tok
);
1028 static enum event_type
force_token(const char *str
, char **tok
)
1030 const char *save_input_buf
;
1031 unsigned long long save_input_buf_ptr
;
1032 unsigned long long save_input_buf_siz
;
1033 enum event_type type
;
1035 /* save off the current input pointers */
1036 save_input_buf
= input_buf
;
1037 save_input_buf_ptr
= input_buf_ptr
;
1038 save_input_buf_siz
= input_buf_siz
;
1040 init_input_buf(str
, strlen(str
));
1042 type
= __read_token(tok
);
1044 /* reset back to original token */
1045 input_buf
= save_input_buf
;
1046 input_buf_ptr
= save_input_buf_ptr
;
1047 input_buf_siz
= save_input_buf_siz
;
1052 static void free_token(char *tok
)
1058 static enum event_type
read_token(char **tok
)
1060 enum event_type type
;
1063 type
= __read_token(tok
);
1064 if (type
!= EVENT_SPACE
)
1076 * pevent_read_token - access to utilites to use the pevent parser
1077 * @tok: The token to return
1079 * This will parse tokens from the string given by
1080 * pevent_init_data().
1082 * Returns the token type.
1084 enum event_type
pevent_read_token(char **tok
)
1086 return read_token(tok
);
1090 * pevent_free_token - free a token returned by pevent_read_token
1091 * @token: the token to free
1093 void pevent_free_token(char *token
)
1099 static enum event_type
read_token_item(char **tok
)
1101 enum event_type type
;
1104 type
= __read_token(tok
);
1105 if (type
!= EVENT_SPACE
&& type
!= EVENT_NEWLINE
)
1116 static int test_type(enum event_type type
, enum event_type expect
)
1118 if (type
!= expect
) {
1119 do_warning("Error: expected type %d but read %d",
1126 static int test_type_token(enum event_type type
, const char *token
,
1127 enum event_type expect
, const char *expect_tok
)
1129 if (type
!= expect
) {
1130 do_warning("Error: expected type %d but read %d",
1135 if (strcmp(token
, expect_tok
) != 0) {
1136 do_warning("Error: expected '%s' but read '%s'",
1143 static int __read_expect_type(enum event_type expect
, char **tok
, int newline_ok
)
1145 enum event_type type
;
1148 type
= read_token(tok
);
1150 type
= read_token_item(tok
);
1151 return test_type(type
, expect
);
1154 static int read_expect_type(enum event_type expect
, char **tok
)
1156 return __read_expect_type(expect
, tok
, 1);
1159 static int __read_expected(enum event_type expect
, const char *str
,
1162 enum event_type type
;
1167 type
= read_token(&token
);
1169 type
= read_token_item(&token
);
1171 ret
= test_type_token(type
, token
, expect
, str
);
1178 static int read_expected(enum event_type expect
, const char *str
)
1180 return __read_expected(expect
, str
, 1);
1183 static int read_expected_item(enum event_type expect
, const char *str
)
1185 return __read_expected(expect
, str
, 0);
1188 static char *event_read_name(void)
1192 if (read_expected(EVENT_ITEM
, "name") < 0)
1195 if (read_expected(EVENT_OP
, ":") < 0)
1198 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
1208 static int event_read_id(void)
1213 if (read_expected_item(EVENT_ITEM
, "ID") < 0)
1216 if (read_expected(EVENT_OP
, ":") < 0)
1219 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
1222 id
= strtoul(token
, NULL
, 0);
1231 static int field_is_string(struct format_field
*field
)
1233 if ((field
->flags
& FIELD_IS_ARRAY
) &&
1234 (strstr(field
->type
, "char") || strstr(field
->type
, "u8") ||
1235 strstr(field
->type
, "s8")))
1241 static int field_is_dynamic(struct format_field
*field
)
1243 if (strncmp(field
->type
, "__data_loc", 10) == 0)
1249 static int field_is_long(struct format_field
*field
)
1251 /* includes long long */
1252 if (strstr(field
->type
, "long"))
1258 static unsigned int type_size(const char *name
)
1260 /* This covers all FIELD_IS_STRING types. */
1278 for (i
= 0; table
[i
].type
; i
++) {
1279 if (!strcmp(table
[i
].type
, name
))
1280 return table
[i
].size
;
1286 static int event_read_fields(struct event_format
*event
, struct format_field
**fields
)
1288 struct format_field
*field
= NULL
;
1289 enum event_type type
;
1295 unsigned int size_dynamic
= 0;
1297 type
= read_token(&token
);
1298 if (type
== EVENT_NEWLINE
) {
1305 if (test_type_token(type
, token
, EVENT_ITEM
, "field"))
1309 type
= read_token(&token
);
1311 * The ftrace fields may still use the "special" name.
1314 if (event
->flags
& EVENT_FL_ISFTRACE
&&
1315 type
== EVENT_ITEM
&& strcmp(token
, "special") == 0) {
1317 type
= read_token(&token
);
1320 if (test_type_token(type
, token
, EVENT_OP
, ":") < 0)
1324 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
1329 field
= calloc(1, sizeof(*field
));
1333 field
->event
= event
;
1335 /* read the rest of the type */
1337 type
= read_token(&token
);
1338 if (type
== EVENT_ITEM
||
1339 (type
== EVENT_OP
&& strcmp(token
, "*") == 0) ||
1341 * Some of the ftrace fields are broken and have
1342 * an illegal "." in them.
1344 (event
->flags
& EVENT_FL_ISFTRACE
&&
1345 type
== EVENT_OP
&& strcmp(token
, ".") == 0)) {
1347 if (strcmp(token
, "*") == 0)
1348 field
->flags
|= FIELD_IS_POINTER
;
1352 new_type
= realloc(field
->type
,
1353 strlen(field
->type
) +
1354 strlen(last_token
) + 2);
1359 field
->type
= new_type
;
1360 strcat(field
->type
, " ");
1361 strcat(field
->type
, last_token
);
1364 field
->type
= last_token
;
1373 do_warning_event(event
, "%s: no type found", __func__
);
1376 field
->name
= last_token
;
1378 if (test_type(type
, EVENT_OP
))
1381 if (strcmp(token
, "[") == 0) {
1382 enum event_type last_type
= type
;
1383 char *brackets
= token
;
1387 field
->flags
|= FIELD_IS_ARRAY
;
1389 type
= read_token(&token
);
1391 if (type
== EVENT_ITEM
)
1392 field
->arraylen
= strtoul(token
, NULL
, 0);
1394 field
->arraylen
= 0;
1396 while (strcmp(token
, "]") != 0) {
1397 if (last_type
== EVENT_ITEM
&&
1404 new_brackets
= realloc(brackets
,
1406 strlen(token
) + len
);
1407 if (!new_brackets
) {
1411 brackets
= new_brackets
;
1413 strcat(brackets
, " ");
1414 strcat(brackets
, token
);
1415 /* We only care about the last token */
1416 field
->arraylen
= strtoul(token
, NULL
, 0);
1418 type
= read_token(&token
);
1419 if (type
== EVENT_NONE
) {
1420 do_warning_event(event
, "failed to find token");
1427 new_brackets
= realloc(brackets
, strlen(brackets
) + 2);
1428 if (!new_brackets
) {
1432 brackets
= new_brackets
;
1433 strcat(brackets
, "]");
1435 /* add brackets to type */
1437 type
= read_token(&token
);
1439 * If the next token is not an OP, then it is of
1440 * the format: type [] item;
1442 if (type
== EVENT_ITEM
) {
1444 new_type
= realloc(field
->type
,
1445 strlen(field
->type
) +
1446 strlen(field
->name
) +
1447 strlen(brackets
) + 2);
1452 field
->type
= new_type
;
1453 strcat(field
->type
, " ");
1454 strcat(field
->type
, field
->name
);
1455 size_dynamic
= type_size(field
->name
);
1456 free_token(field
->name
);
1457 strcat(field
->type
, brackets
);
1458 field
->name
= token
;
1459 type
= read_token(&token
);
1462 new_type
= realloc(field
->type
,
1463 strlen(field
->type
) +
1464 strlen(brackets
) + 1);
1469 field
->type
= new_type
;
1470 strcat(field
->type
, brackets
);
1475 if (field_is_string(field
))
1476 field
->flags
|= FIELD_IS_STRING
;
1477 if (field_is_dynamic(field
))
1478 field
->flags
|= FIELD_IS_DYNAMIC
;
1479 if (field_is_long(field
))
1480 field
->flags
|= FIELD_IS_LONG
;
1482 if (test_type_token(type
, token
, EVENT_OP
, ";"))
1486 if (read_expected(EVENT_ITEM
, "offset") < 0)
1489 if (read_expected(EVENT_OP
, ":") < 0)
1492 if (read_expect_type(EVENT_ITEM
, &token
))
1494 field
->offset
= strtoul(token
, NULL
, 0);
1497 if (read_expected(EVENT_OP
, ";") < 0)
1500 if (read_expected(EVENT_ITEM
, "size") < 0)
1503 if (read_expected(EVENT_OP
, ":") < 0)
1506 if (read_expect_type(EVENT_ITEM
, &token
))
1508 field
->size
= strtoul(token
, NULL
, 0);
1511 if (read_expected(EVENT_OP
, ";") < 0)
1514 type
= read_token(&token
);
1515 if (type
!= EVENT_NEWLINE
) {
1516 /* newer versions of the kernel have a "signed" type */
1517 if (test_type_token(type
, token
, EVENT_ITEM
, "signed"))
1522 if (read_expected(EVENT_OP
, ":") < 0)
1525 if (read_expect_type(EVENT_ITEM
, &token
))
1528 if (strtoul(token
, NULL
, 0))
1529 field
->flags
|= FIELD_IS_SIGNED
;
1532 if (read_expected(EVENT_OP
, ";") < 0)
1535 if (read_expect_type(EVENT_NEWLINE
, &token
))
1541 if (field
->flags
& FIELD_IS_ARRAY
) {
1542 if (field
->arraylen
)
1543 field
->elementsize
= field
->size
/ field
->arraylen
;
1544 else if (field
->flags
& FIELD_IS_DYNAMIC
)
1545 field
->elementsize
= size_dynamic
;
1546 else if (field
->flags
& FIELD_IS_STRING
)
1547 field
->elementsize
= 1;
1548 else if (field
->flags
& FIELD_IS_LONG
)
1549 field
->elementsize
= event
->pevent
?
1550 event
->pevent
->long_size
:
1553 field
->elementsize
= field
->size
;
1556 fields
= &field
->next
;
1573 static int event_read_format(struct event_format
*event
)
1578 if (read_expected_item(EVENT_ITEM
, "format") < 0)
1581 if (read_expected(EVENT_OP
, ":") < 0)
1584 if (read_expect_type(EVENT_NEWLINE
, &token
))
1588 ret
= event_read_fields(event
, &event
->format
.common_fields
);
1591 event
->format
.nr_common
= ret
;
1593 ret
= event_read_fields(event
, &event
->format
.fields
);
1596 event
->format
.nr_fields
= ret
;
1605 static enum event_type
1606 process_arg_token(struct event_format
*event
, struct print_arg
*arg
,
1607 char **tok
, enum event_type type
);
1609 static enum event_type
1610 process_arg(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
1612 enum event_type type
;
1615 type
= read_token(&token
);
1618 return process_arg_token(event
, arg
, tok
, type
);
1621 static enum event_type
1622 process_op(struct event_format
*event
, struct print_arg
*arg
, char **tok
);
1625 * For __print_symbolic() and __print_flags, we need to completely
1626 * evaluate the first argument, which defines what to print next.
1628 static enum event_type
1629 process_field_arg(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
1631 enum event_type type
;
1633 type
= process_arg(event
, arg
, tok
);
1635 while (type
== EVENT_OP
) {
1636 type
= process_op(event
, arg
, tok
);
1642 static enum event_type
1643 process_cond(struct event_format
*event
, struct print_arg
*top
, char **tok
)
1645 struct print_arg
*arg
, *left
, *right
;
1646 enum event_type type
;
1651 right
= alloc_arg();
1653 if (!arg
|| !left
|| !right
) {
1654 do_warning_event(event
, "%s: not enough memory!", __func__
);
1655 /* arg will be freed at out_free */
1661 arg
->type
= PRINT_OP
;
1662 arg
->op
.left
= left
;
1663 arg
->op
.right
= right
;
1666 type
= process_arg(event
, left
, &token
);
1669 /* Handle other operations in the arguments */
1670 if (type
== EVENT_OP
&& strcmp(token
, ":") != 0) {
1671 type
= process_op(event
, left
, &token
);
1675 if (test_type_token(type
, token
, EVENT_OP
, ":"))
1680 type
= process_arg(event
, right
, &token
);
1682 top
->op
.right
= arg
;
1688 /* Top may point to itself */
1689 top
->op
.right
= NULL
;
1695 static enum event_type
1696 process_array(struct event_format
*event
, struct print_arg
*top
, char **tok
)
1698 struct print_arg
*arg
;
1699 enum event_type type
;
1704 do_warning_event(event
, "%s: not enough memory!", __func__
);
1705 /* '*tok' is set to top->op.op. No need to free. */
1711 type
= process_arg(event
, arg
, &token
);
1712 if (test_type_token(type
, token
, EVENT_OP
, "]"))
1715 top
->op
.right
= arg
;
1718 type
= read_token_item(&token
);
1729 static int get_op_prio(char *op
)
1743 /* '>>' and '<<' are 8 */
1747 /* '==' and '!=' are 10 */
1757 do_warning("unknown op '%c'", op
[0]);
1761 if (strcmp(op
, "++") == 0 ||
1762 strcmp(op
, "--") == 0) {
1764 } else if (strcmp(op
, ">>") == 0 ||
1765 strcmp(op
, "<<") == 0) {
1767 } else if (strcmp(op
, ">=") == 0 ||
1768 strcmp(op
, "<=") == 0) {
1770 } else if (strcmp(op
, "==") == 0 ||
1771 strcmp(op
, "!=") == 0) {
1773 } else if (strcmp(op
, "&&") == 0) {
1775 } else if (strcmp(op
, "||") == 0) {
1778 do_warning("unknown op '%s'", op
);
1784 static int set_op_prio(struct print_arg
*arg
)
1787 /* single ops are the greatest */
1788 if (!arg
->op
.left
|| arg
->op
.left
->type
== PRINT_NULL
)
1791 arg
->op
.prio
= get_op_prio(arg
->op
.op
);
1793 return arg
->op
.prio
;
1796 /* Note, *tok does not get freed, but will most likely be saved */
1797 static enum event_type
1798 process_op(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
1800 struct print_arg
*left
, *right
= NULL
;
1801 enum event_type type
;
1804 /* the op is passed in via tok */
1807 if (arg
->type
== PRINT_OP
&& !arg
->op
.left
) {
1808 /* handle single op */
1810 do_warning_event(event
, "bad op token %s", token
);
1820 do_warning_event(event
, "bad op token %s", token
);
1825 /* make an empty left */
1830 left
->type
= PRINT_NULL
;
1831 arg
->op
.left
= left
;
1833 right
= alloc_arg();
1837 arg
->op
.right
= right
;
1839 /* do not free the token, it belongs to an op */
1841 type
= process_arg(event
, right
, tok
);
1843 } else if (strcmp(token
, "?") == 0) {
1849 /* copy the top arg to the left */
1852 arg
->type
= PRINT_OP
;
1854 arg
->op
.left
= left
;
1857 /* it will set arg->op.right */
1858 type
= process_cond(event
, arg
, tok
);
1860 } else if (strcmp(token
, ">>") == 0 ||
1861 strcmp(token
, "<<") == 0 ||
1862 strcmp(token
, "&") == 0 ||
1863 strcmp(token
, "|") == 0 ||
1864 strcmp(token
, "&&") == 0 ||
1865 strcmp(token
, "||") == 0 ||
1866 strcmp(token
, "-") == 0 ||
1867 strcmp(token
, "+") == 0 ||
1868 strcmp(token
, "*") == 0 ||
1869 strcmp(token
, "^") == 0 ||
1870 strcmp(token
, "/") == 0 ||
1871 strcmp(token
, "<") == 0 ||
1872 strcmp(token
, ">") == 0 ||
1873 strcmp(token
, "<=") == 0 ||
1874 strcmp(token
, ">=") == 0 ||
1875 strcmp(token
, "==") == 0 ||
1876 strcmp(token
, "!=") == 0) {
1882 /* copy the top arg to the left */
1885 arg
->type
= PRINT_OP
;
1887 arg
->op
.left
= left
;
1888 arg
->op
.right
= NULL
;
1890 if (set_op_prio(arg
) == -1) {
1891 event
->flags
|= EVENT_FL_FAILED
;
1892 /* arg->op.op (= token) will be freed at out_free */
1897 type
= read_token_item(&token
);
1900 /* could just be a type pointer */
1901 if ((strcmp(arg
->op
.op
, "*") == 0) &&
1902 type
== EVENT_DELIM
&& (strcmp(token
, ")") == 0)) {
1905 if (left
->type
!= PRINT_ATOM
) {
1906 do_warning_event(event
, "bad pointer type");
1909 new_atom
= realloc(left
->atom
.atom
,
1910 strlen(left
->atom
.atom
) + 3);
1914 left
->atom
.atom
= new_atom
;
1915 strcat(left
->atom
.atom
, " *");
1923 right
= alloc_arg();
1927 type
= process_arg_token(event
, right
, tok
, type
);
1928 arg
->op
.right
= right
;
1930 } else if (strcmp(token
, "[") == 0) {
1938 arg
->type
= PRINT_OP
;
1940 arg
->op
.left
= left
;
1944 /* it will set arg->op.right */
1945 type
= process_array(event
, arg
, tok
);
1948 do_warning_event(event
, "unknown op '%s'", token
);
1949 event
->flags
|= EVENT_FL_FAILED
;
1950 /* the arg is now the left side */
1954 if (type
== EVENT_OP
&& strcmp(*tok
, ":") != 0) {
1957 /* higher prios need to be closer to the root */
1958 prio
= get_op_prio(*tok
);
1960 if (prio
> arg
->op
.prio
)
1961 return process_op(event
, arg
, tok
);
1963 return process_op(event
, right
, tok
);
1969 do_warning_event(event
, "%s: not enough memory!", __func__
);
1976 static enum event_type
1977 process_entry(struct event_format
*event __maybe_unused
, struct print_arg
*arg
,
1980 enum event_type type
;
1984 if (read_expected(EVENT_OP
, "->") < 0)
1987 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
1991 arg
->type
= PRINT_FIELD
;
1992 arg
->field
.name
= field
;
1994 if (is_flag_field
) {
1995 arg
->field
.field
= pevent_find_any_field(event
, arg
->field
.name
);
1996 arg
->field
.field
->flags
|= FIELD_IS_FLAG
;
1998 } else if (is_symbolic_field
) {
1999 arg
->field
.field
= pevent_find_any_field(event
, arg
->field
.name
);
2000 arg
->field
.field
->flags
|= FIELD_IS_SYMBOLIC
;
2001 is_symbolic_field
= 0;
2004 type
= read_token(&token
);
2016 static char *arg_eval (struct print_arg
*arg
);
2018 static unsigned long long
2019 eval_type_str(unsigned long long val
, const char *type
, int pointer
)
2029 if (type
[len
-1] != '*') {
2030 do_warning("pointer expected with non pointer type");
2036 do_warning("%s: not enough memory!", __func__
);
2039 memcpy(ref
, type
, len
);
2041 /* chop off the " *" */
2044 val
= eval_type_str(val
, ref
, 0);
2049 /* check if this is a pointer */
2050 if (type
[len
- 1] == '*')
2053 /* Try to figure out the arg size*/
2054 if (strncmp(type
, "struct", 6) == 0)
2058 if (strcmp(type
, "u8") == 0)
2061 if (strcmp(type
, "u16") == 0)
2062 return val
& 0xffff;
2064 if (strcmp(type
, "u32") == 0)
2065 return val
& 0xffffffff;
2067 if (strcmp(type
, "u64") == 0 ||
2068 strcmp(type
, "s64"))
2071 if (strcmp(type
, "s8") == 0)
2072 return (unsigned long long)(char)val
& 0xff;
2074 if (strcmp(type
, "s16") == 0)
2075 return (unsigned long long)(short)val
& 0xffff;
2077 if (strcmp(type
, "s32") == 0)
2078 return (unsigned long long)(int)val
& 0xffffffff;
2080 if (strncmp(type
, "unsigned ", 9) == 0) {
2085 if (strcmp(type
, "char") == 0) {
2087 return (unsigned long long)(char)val
& 0xff;
2092 if (strcmp(type
, "short") == 0) {
2094 return (unsigned long long)(short)val
& 0xffff;
2096 return val
& 0xffff;
2099 if (strcmp(type
, "int") == 0) {
2101 return (unsigned long long)(int)val
& 0xffffffff;
2103 return val
& 0xffffffff;
2110 * Try to figure out the type.
2112 static unsigned long long
2113 eval_type(unsigned long long val
, struct print_arg
*arg
, int pointer
)
2115 if (arg
->type
!= PRINT_TYPE
) {
2116 do_warning("expected type argument");
2120 return eval_type_str(val
, arg
->typecast
.type
, pointer
);
2123 static int arg_num_eval(struct print_arg
*arg
, long long *val
)
2125 long long left
, right
;
2128 switch (arg
->type
) {
2130 *val
= strtoll(arg
->atom
.atom
, NULL
, 0);
2133 ret
= arg_num_eval(arg
->typecast
.item
, val
);
2136 *val
= eval_type(*val
, arg
, 0);
2139 switch (arg
->op
.op
[0]) {
2141 ret
= arg_num_eval(arg
->op
.left
, &left
);
2144 ret
= arg_num_eval(arg
->op
.right
, &right
);
2148 *val
= left
|| right
;
2150 *val
= left
| right
;
2153 ret
= arg_num_eval(arg
->op
.left
, &left
);
2156 ret
= arg_num_eval(arg
->op
.right
, &right
);
2160 *val
= left
&& right
;
2162 *val
= left
& right
;
2165 ret
= arg_num_eval(arg
->op
.left
, &left
);
2168 ret
= arg_num_eval(arg
->op
.right
, &right
);
2171 switch (arg
->op
.op
[1]) {
2173 *val
= left
< right
;
2176 *val
= left
<< right
;
2179 *val
= left
<= right
;
2182 do_warning("unknown op '%s'", arg
->op
.op
);
2187 ret
= arg_num_eval(arg
->op
.left
, &left
);
2190 ret
= arg_num_eval(arg
->op
.right
, &right
);
2193 switch (arg
->op
.op
[1]) {
2195 *val
= left
> right
;
2198 *val
= left
>> right
;
2201 *val
= left
>= right
;
2204 do_warning("unknown op '%s'", arg
->op
.op
);
2209 ret
= arg_num_eval(arg
->op
.left
, &left
);
2212 ret
= arg_num_eval(arg
->op
.right
, &right
);
2216 if (arg
->op
.op
[1] != '=') {
2217 do_warning("unknown op '%s'", arg
->op
.op
);
2220 *val
= left
== right
;
2223 ret
= arg_num_eval(arg
->op
.left
, &left
);
2226 ret
= arg_num_eval(arg
->op
.right
, &right
);
2230 switch (arg
->op
.op
[1]) {
2232 *val
= left
!= right
;
2235 do_warning("unknown op '%s'", arg
->op
.op
);
2240 /* check for negative */
2241 if (arg
->op
.left
->type
== PRINT_NULL
)
2244 ret
= arg_num_eval(arg
->op
.left
, &left
);
2247 ret
= arg_num_eval(arg
->op
.right
, &right
);
2250 *val
= left
- right
;
2253 if (arg
->op
.left
->type
== PRINT_NULL
)
2256 ret
= arg_num_eval(arg
->op
.left
, &left
);
2259 ret
= arg_num_eval(arg
->op
.right
, &right
);
2262 *val
= left
+ right
;
2265 do_warning("unknown op '%s'", arg
->op
.op
);
2271 case PRINT_FIELD
... PRINT_SYMBOL
:
2276 do_warning("invalid eval type %d", arg
->type
);
2283 static char *arg_eval (struct print_arg
*arg
)
2286 static char buf
[20];
2288 switch (arg
->type
) {
2290 return arg
->atom
.atom
;
2292 return arg_eval(arg
->typecast
.item
);
2294 if (!arg_num_eval(arg
, &val
))
2296 sprintf(buf
, "%lld", val
);
2300 case PRINT_FIELD
... PRINT_SYMBOL
:
2305 do_warning("invalid eval type %d", arg
->type
);
2312 static enum event_type
2313 process_fields(struct event_format
*event
, struct print_flag_sym
**list
, char **tok
)
2315 enum event_type type
;
2316 struct print_arg
*arg
= NULL
;
2317 struct print_flag_sym
*field
;
2323 type
= read_token_item(&token
);
2324 if (test_type_token(type
, token
, EVENT_OP
, "{"))
2332 type
= process_arg(event
, arg
, &token
);
2334 if (type
== EVENT_OP
)
2335 type
= process_op(event
, arg
, &token
);
2337 if (type
== EVENT_ERROR
)
2340 if (test_type_token(type
, token
, EVENT_DELIM
, ","))
2343 field
= calloc(1, sizeof(*field
));
2347 value
= arg_eval(arg
);
2349 goto out_free_field
;
2350 field
->value
= strdup(value
);
2351 if (field
->value
== NULL
)
2352 goto out_free_field
;
2360 type
= process_arg(event
, arg
, &token
);
2361 if (test_type_token(type
, token
, EVENT_OP
, "}"))
2362 goto out_free_field
;
2364 value
= arg_eval(arg
);
2366 goto out_free_field
;
2367 field
->str
= strdup(value
);
2368 if (field
->str
== NULL
)
2369 goto out_free_field
;
2374 list
= &field
->next
;
2377 type
= read_token_item(&token
);
2378 } while (type
== EVENT_DELIM
&& strcmp(token
, ",") == 0);
2384 free_flag_sym(field
);
2393 static enum event_type
2394 process_flags(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
2396 struct print_arg
*field
;
2397 enum event_type type
;
2400 memset(arg
, 0, sizeof(*arg
));
2401 arg
->type
= PRINT_FLAGS
;
2403 field
= alloc_arg();
2405 do_warning_event(event
, "%s: not enough memory!", __func__
);
2409 type
= process_field_arg(event
, field
, &token
);
2411 /* Handle operations in the first argument */
2412 while (type
== EVENT_OP
)
2413 type
= process_op(event
, field
, &token
);
2415 if (test_type_token(type
, token
, EVENT_DELIM
, ","))
2416 goto out_free_field
;
2419 arg
->flags
.field
= field
;
2421 type
= read_token_item(&token
);
2422 if (event_item_type(type
)) {
2423 arg
->flags
.delim
= token
;
2424 type
= read_token_item(&token
);
2427 if (test_type_token(type
, token
, EVENT_DELIM
, ","))
2430 type
= process_fields(event
, &arg
->flags
.flags
, &token
);
2431 if (test_type_token(type
, token
, EVENT_DELIM
, ")"))
2435 type
= read_token_item(tok
);
2446 static enum event_type
2447 process_symbols(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
2449 struct print_arg
*field
;
2450 enum event_type type
;
2453 memset(arg
, 0, sizeof(*arg
));
2454 arg
->type
= PRINT_SYMBOL
;
2456 field
= alloc_arg();
2458 do_warning_event(event
, "%s: not enough memory!", __func__
);
2462 type
= process_field_arg(event
, field
, &token
);
2464 if (test_type_token(type
, token
, EVENT_DELIM
, ","))
2465 goto out_free_field
;
2467 arg
->symbol
.field
= field
;
2469 type
= process_fields(event
, &arg
->symbol
.symbols
, &token
);
2470 if (test_type_token(type
, token
, EVENT_DELIM
, ")"))
2474 type
= read_token_item(tok
);
2485 static enum event_type
2486 process_hex(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
2488 struct print_arg
*field
;
2489 enum event_type type
;
2492 memset(arg
, 0, sizeof(*arg
));
2493 arg
->type
= PRINT_HEX
;
2495 field
= alloc_arg();
2497 do_warning_event(event
, "%s: not enough memory!", __func__
);
2501 type
= process_arg(event
, field
, &token
);
2503 if (test_type_token(type
, token
, EVENT_DELIM
, ","))
2506 arg
->hex
.field
= field
;
2510 field
= alloc_arg();
2512 do_warning_event(event
, "%s: not enough memory!", __func__
);
2517 type
= process_arg(event
, field
, &token
);
2519 if (test_type_token(type
, token
, EVENT_DELIM
, ")"))
2522 arg
->hex
.size
= field
;
2525 type
= read_token_item(tok
);
2535 static enum event_type
2536 process_dynamic_array(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
2538 struct format_field
*field
;
2539 enum event_type type
;
2542 memset(arg
, 0, sizeof(*arg
));
2543 arg
->type
= PRINT_DYNAMIC_ARRAY
;
2546 * The item within the parenthesis is another field that holds
2547 * the index into where the array starts.
2549 type
= read_token(&token
);
2551 if (type
!= EVENT_ITEM
)
2554 /* Find the field */
2556 field
= pevent_find_field(event
, token
);
2560 arg
->dynarray
.field
= field
;
2561 arg
->dynarray
.index
= 0;
2563 if (read_expected(EVENT_DELIM
, ")") < 0)
2567 type
= read_token_item(&token
);
2569 if (type
!= EVENT_OP
|| strcmp(token
, "[") != 0)
2575 do_warning_event(event
, "%s: not enough memory!", __func__
);
2580 type
= process_arg(event
, arg
, &token
);
2581 if (type
== EVENT_ERROR
)
2584 if (!test_type_token(type
, token
, EVENT_OP
, "]"))
2588 type
= read_token_item(tok
);
2599 static enum event_type
2600 process_paren(struct event_format
*event
, struct print_arg
*arg
, char **tok
)
2602 struct print_arg
*item_arg
;
2603 enum event_type type
;
2606 type
= process_arg(event
, arg
, &token
);
2608 if (type
== EVENT_ERROR
)
2611 if (type
== EVENT_OP
)
2612 type
= process_op(event
, arg
, &token
);
2614 if (type
== EVENT_ERROR
)
2617 if (test_type_token(type
, token
, EVENT_DELIM
, ")"))
2621 type
= read_token_item(&token
);
2624 * If the next token is an item or another open paren, then
2625 * this was a typecast.
2627 if (event_item_type(type
) ||
2628 (type
== EVENT_DELIM
&& strcmp(token
, "(") == 0)) {
2630 /* make this a typecast and contine */
2632 /* prevous must be an atom */
2633 if (arg
->type
!= PRINT_ATOM
) {
2634 do_warning_event(event
, "previous needed to be PRINT_ATOM");
2638 item_arg
= alloc_arg();
2640 do_warning_event(event
, "%s: not enough memory!",
2645 arg
->type
= PRINT_TYPE
;
2646 arg
->typecast
.type
= arg
->atom
.atom
;
2647 arg
->typecast
.item
= item_arg
;
2648 type
= process_arg_token(event
, item_arg
, &token
, type
);
2662 static enum event_type
2663 process_str(struct event_format
*event __maybe_unused
, struct print_arg
*arg
,
2666 enum event_type type
;
2669 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
2672 arg
->type
= PRINT_STRING
;
2673 arg
->string
.string
= token
;
2674 arg
->string
.offset
= -1;
2676 if (read_expected(EVENT_DELIM
, ")") < 0)
2679 type
= read_token(&token
);
2691 static enum event_type
2692 process_bitmask(struct event_format
*event __maybe_unused
, struct print_arg
*arg
,
2695 enum event_type type
;
2698 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
2701 arg
->type
= PRINT_BITMASK
;
2702 arg
->bitmask
.bitmask
= token
;
2703 arg
->bitmask
.offset
= -1;
2705 if (read_expected(EVENT_DELIM
, ")") < 0)
2708 type
= read_token(&token
);
2720 static struct pevent_function_handler
*
2721 find_func_handler(struct pevent
*pevent
, char *func_name
)
2723 struct pevent_function_handler
*func
;
2728 for (func
= pevent
->func_handlers
; func
; func
= func
->next
) {
2729 if (strcmp(func
->name
, func_name
) == 0)
2736 static void remove_func_handler(struct pevent
*pevent
, char *func_name
)
2738 struct pevent_function_handler
*func
;
2739 struct pevent_function_handler
**next
;
2741 next
= &pevent
->func_handlers
;
2742 while ((func
= *next
)) {
2743 if (strcmp(func
->name
, func_name
) == 0) {
2745 free_func_handle(func
);
2752 static enum event_type
2753 process_func_handler(struct event_format
*event
, struct pevent_function_handler
*func
,
2754 struct print_arg
*arg
, char **tok
)
2756 struct print_arg
**next_arg
;
2757 struct print_arg
*farg
;
2758 enum event_type type
;
2762 arg
->type
= PRINT_FUNC
;
2763 arg
->func
.func
= func
;
2767 next_arg
= &(arg
->func
.args
);
2768 for (i
= 0; i
< func
->nr_args
; i
++) {
2771 do_warning_event(event
, "%s: not enough memory!",
2776 type
= process_arg(event
, farg
, &token
);
2777 if (i
< (func
->nr_args
- 1)) {
2778 if (type
!= EVENT_DELIM
|| strcmp(token
, ",") != 0) {
2779 do_warning_event(event
,
2780 "Error: function '%s()' expects %d arguments but event %s only uses %d",
2781 func
->name
, func
->nr_args
,
2782 event
->name
, i
+ 1);
2786 if (type
!= EVENT_DELIM
|| strcmp(token
, ")") != 0) {
2787 do_warning_event(event
,
2788 "Error: function '%s()' only expects %d arguments but event %s has more",
2789 func
->name
, func
->nr_args
, event
->name
);
2795 next_arg
= &(farg
->next
);
2799 type
= read_token(&token
);
2810 static enum event_type
2811 process_function(struct event_format
*event
, struct print_arg
*arg
,
2812 char *token
, char **tok
)
2814 struct pevent_function_handler
*func
;
2816 if (strcmp(token
, "__print_flags") == 0) {
2819 return process_flags(event
, arg
, tok
);
2821 if (strcmp(token
, "__print_symbolic") == 0) {
2823 is_symbolic_field
= 1;
2824 return process_symbols(event
, arg
, tok
);
2826 if (strcmp(token
, "__print_hex") == 0) {
2828 return process_hex(event
, arg
, tok
);
2830 if (strcmp(token
, "__get_str") == 0) {
2832 return process_str(event
, arg
, tok
);
2834 if (strcmp(token
, "__get_bitmask") == 0) {
2836 return process_bitmask(event
, arg
, tok
);
2838 if (strcmp(token
, "__get_dynamic_array") == 0) {
2840 return process_dynamic_array(event
, arg
, tok
);
2843 func
= find_func_handler(event
->pevent
, token
);
2846 return process_func_handler(event
, func
, arg
, tok
);
2849 do_warning_event(event
, "function %s not defined", token
);
2854 static enum event_type
2855 process_arg_token(struct event_format
*event
, struct print_arg
*arg
,
2856 char **tok
, enum event_type type
)
2865 if (strcmp(token
, "REC") == 0) {
2867 type
= process_entry(event
, arg
, &token
);
2871 /* test the next token */
2872 type
= read_token_item(&token
);
2875 * If the next token is a parenthesis, then this
2878 if (type
== EVENT_DELIM
&& strcmp(token
, "(") == 0) {
2881 /* this will free atom. */
2882 type
= process_function(event
, arg
, atom
, &token
);
2885 /* atoms can be more than one token long */
2886 while (type
== EVENT_ITEM
) {
2888 new_atom
= realloc(atom
,
2889 strlen(atom
) + strlen(token
) + 2);
2898 strcat(atom
, token
);
2900 type
= read_token_item(&token
);
2903 arg
->type
= PRINT_ATOM
;
2904 arg
->atom
.atom
= atom
;
2909 arg
->type
= PRINT_ATOM
;
2910 arg
->atom
.atom
= token
;
2911 type
= read_token_item(&token
);
2914 if (strcmp(token
, "(") == 0) {
2916 type
= process_paren(event
, arg
, &token
);
2920 /* handle single ops */
2921 arg
->type
= PRINT_OP
;
2923 arg
->op
.left
= NULL
;
2924 type
= process_op(event
, arg
, &token
);
2926 /* On error, the op is freed */
2927 if (type
== EVENT_ERROR
)
2930 /* return error type if errored */
2933 case EVENT_ERROR
... EVENT_NEWLINE
:
2935 do_warning_event(event
, "unexpected type %d", type
);
2943 static int event_read_print_args(struct event_format
*event
, struct print_arg
**list
)
2945 enum event_type type
= EVENT_ERROR
;
2946 struct print_arg
*arg
;
2951 if (type
== EVENT_NEWLINE
) {
2952 type
= read_token_item(&token
);
2958 do_warning_event(event
, "%s: not enough memory!",
2963 type
= process_arg(event
, arg
, &token
);
2965 if (type
== EVENT_ERROR
) {
2974 if (type
== EVENT_OP
) {
2975 type
= process_op(event
, arg
, &token
);
2977 if (type
== EVENT_ERROR
) {
2986 if (type
== EVENT_DELIM
&& strcmp(token
, ",") == 0) {
2993 } while (type
!= EVENT_NONE
);
2995 if (type
!= EVENT_NONE
&& type
!= EVENT_ERROR
)
3001 static int event_read_print(struct event_format
*event
)
3003 enum event_type type
;
3007 if (read_expected_item(EVENT_ITEM
, "print") < 0)
3010 if (read_expected(EVENT_ITEM
, "fmt") < 0)
3013 if (read_expected(EVENT_OP
, ":") < 0)
3016 if (read_expect_type(EVENT_DQUOTE
, &token
) < 0)
3020 event
->print_fmt
.format
= token
;
3021 event
->print_fmt
.args
= NULL
;
3023 /* ok to have no arg */
3024 type
= read_token_item(&token
);
3026 if (type
== EVENT_NONE
)
3029 /* Handle concatenation of print lines */
3030 if (type
== EVENT_DQUOTE
) {
3033 if (asprintf(&cat
, "%s%s", event
->print_fmt
.format
, token
) < 0)
3036 free_token(event
->print_fmt
.format
);
3037 event
->print_fmt
.format
= NULL
;
3042 if (test_type_token(type
, token
, EVENT_DELIM
, ","))
3047 ret
= event_read_print_args(event
, &event
->print_fmt
.args
);
3059 * pevent_find_common_field - return a common field by event
3060 * @event: handle for the event
3061 * @name: the name of the common field to return
3063 * Returns a common field from the event by the given @name.
3064 * This only searchs the common fields and not all field.
3066 struct format_field
*
3067 pevent_find_common_field(struct event_format
*event
, const char *name
)
3069 struct format_field
*format
;
3071 for (format
= event
->format
.common_fields
;
3072 format
; format
= format
->next
) {
3073 if (strcmp(format
->name
, name
) == 0)
3081 * pevent_find_field - find a non-common field
3082 * @event: handle for the event
3083 * @name: the name of the non-common field
3085 * Returns a non-common field by the given @name.
3086 * This does not search common fields.
3088 struct format_field
*
3089 pevent_find_field(struct event_format
*event
, const char *name
)
3091 struct format_field
*format
;
3093 for (format
= event
->format
.fields
;
3094 format
; format
= format
->next
) {
3095 if (strcmp(format
->name
, name
) == 0)
3103 * pevent_find_any_field - find any field by name
3104 * @event: handle for the event
3105 * @name: the name of the field
3107 * Returns a field by the given @name.
3108 * This searchs the common field names first, then
3109 * the non-common ones if a common one was not found.
3111 struct format_field
*
3112 pevent_find_any_field(struct event_format
*event
, const char *name
)
3114 struct format_field
*format
;
3116 format
= pevent_find_common_field(event
, name
);
3119 return pevent_find_field(event
, name
);
3123 * pevent_read_number - read a number from data
3124 * @pevent: handle for the pevent
3125 * @ptr: the raw data
3126 * @size: the size of the data that holds the number
3128 * Returns the number (converted to host) from the
3131 unsigned long long pevent_read_number(struct pevent
*pevent
,
3132 const void *ptr
, int size
)
3136 return *(unsigned char *)ptr
;
3138 return data2host2(pevent
, ptr
);
3140 return data2host4(pevent
, ptr
);
3142 return data2host8(pevent
, ptr
);
3150 * pevent_read_number_field - read a number from data
3151 * @field: a handle to the field
3152 * @data: the raw data to read
3153 * @value: the value to place the number in
3155 * Reads raw data according to a field offset and size,
3156 * and translates it into @value.
3158 * Returns 0 on success, -1 otherwise.
3160 int pevent_read_number_field(struct format_field
*field
, const void *data
,
3161 unsigned long long *value
)
3165 switch (field
->size
) {
3170 *value
= pevent_read_number(field
->event
->pevent
,
3171 data
+ field
->offset
, field
->size
);
3178 static int get_common_info(struct pevent
*pevent
,
3179 const char *type
, int *offset
, int *size
)
3181 struct event_format
*event
;
3182 struct format_field
*field
;
3185 * All events should have the same common elements.
3186 * Pick any event to find where the type is;
3188 if (!pevent
->events
) {
3189 do_warning("no event_list!");
3193 event
= pevent
->events
[0];
3194 field
= pevent_find_common_field(event
, type
);
3198 *offset
= field
->offset
;
3199 *size
= field
->size
;
3204 static int __parse_common(struct pevent
*pevent
, void *data
,
3205 int *size
, int *offset
, const char *name
)
3210 ret
= get_common_info(pevent
, name
, offset
, size
);
3214 return pevent_read_number(pevent
, data
+ *offset
, *size
);
3217 static int trace_parse_common_type(struct pevent
*pevent
, void *data
)
3219 return __parse_common(pevent
, data
,
3220 &pevent
->type_size
, &pevent
->type_offset
,
3224 static int parse_common_pid(struct pevent
*pevent
, void *data
)
3226 return __parse_common(pevent
, data
,
3227 &pevent
->pid_size
, &pevent
->pid_offset
,
3231 static int parse_common_pc(struct pevent
*pevent
, void *data
)
3233 return __parse_common(pevent
, data
,
3234 &pevent
->pc_size
, &pevent
->pc_offset
,
3235 "common_preempt_count");
3238 static int parse_common_flags(struct pevent
*pevent
, void *data
)
3240 return __parse_common(pevent
, data
,
3241 &pevent
->flags_size
, &pevent
->flags_offset
,
3245 static int parse_common_lock_depth(struct pevent
*pevent
, void *data
)
3247 return __parse_common(pevent
, data
,
3248 &pevent
->ld_size
, &pevent
->ld_offset
,
3249 "common_lock_depth");
3252 static int parse_common_migrate_disable(struct pevent
*pevent
, void *data
)
3254 return __parse_common(pevent
, data
,
3255 &pevent
->ld_size
, &pevent
->ld_offset
,
3256 "common_migrate_disable");
3259 static int events_id_cmp(const void *a
, const void *b
);
3262 * pevent_find_event - find an event by given id
3263 * @pevent: a handle to the pevent
3264 * @id: the id of the event
3266 * Returns an event that has a given @id.
3268 struct event_format
*pevent_find_event(struct pevent
*pevent
, int id
)
3270 struct event_format
**eventptr
;
3271 struct event_format key
;
3272 struct event_format
*pkey
= &key
;
3274 /* Check cache first */
3275 if (pevent
->last_event
&& pevent
->last_event
->id
== id
)
3276 return pevent
->last_event
;
3280 eventptr
= bsearch(&pkey
, pevent
->events
, pevent
->nr_events
,
3281 sizeof(*pevent
->events
), events_id_cmp
);
3284 pevent
->last_event
= *eventptr
;
3292 * pevent_find_event_by_name - find an event by given name
3293 * @pevent: a handle to the pevent
3294 * @sys: the system name to search for
3295 * @name: the name of the event to search for
3297 * This returns an event with a given @name and under the system
3298 * @sys. If @sys is NULL the first event with @name is returned.
3300 struct event_format
*
3301 pevent_find_event_by_name(struct pevent
*pevent
,
3302 const char *sys
, const char *name
)
3304 struct event_format
*event
;
3307 if (pevent
->last_event
&&
3308 strcmp(pevent
->last_event
->name
, name
) == 0 &&
3309 (!sys
|| strcmp(pevent
->last_event
->system
, sys
) == 0))
3310 return pevent
->last_event
;
3312 for (i
= 0; i
< pevent
->nr_events
; i
++) {
3313 event
= pevent
->events
[i
];
3314 if (strcmp(event
->name
, name
) == 0) {
3317 if (strcmp(event
->system
, sys
) == 0)
3321 if (i
== pevent
->nr_events
)
3324 pevent
->last_event
= event
;
3328 static unsigned long long
3329 eval_num_arg(void *data
, int size
, struct event_format
*event
, struct print_arg
*arg
)
3331 struct pevent
*pevent
= event
->pevent
;
3332 unsigned long long val
= 0;
3333 unsigned long long left
, right
;
3334 struct print_arg
*typearg
= NULL
;
3335 struct print_arg
*larg
;
3336 unsigned long offset
;
3337 unsigned int field_size
;
3339 switch (arg
->type
) {
3344 return strtoull(arg
->atom
.atom
, NULL
, 0);
3346 if (!arg
->field
.field
) {
3347 arg
->field
.field
= pevent_find_any_field(event
, arg
->field
.name
);
3348 if (!arg
->field
.field
)
3349 goto out_warning_field
;
3352 /* must be a number */
3353 val
= pevent_read_number(pevent
, data
+ arg
->field
.field
->offset
,
3354 arg
->field
.field
->size
);
3361 val
= eval_num_arg(data
, size
, event
, arg
->typecast
.item
);
3362 return eval_type(val
, arg
, 0);
3370 val
= process_defined_func(&s
, data
, size
, event
, arg
);
3371 trace_seq_destroy(&s
);
3375 if (strcmp(arg
->op
.op
, "[") == 0) {
3377 * Arrays are special, since we don't want
3378 * to read the arg as is.
3380 right
= eval_num_arg(data
, size
, event
, arg
->op
.right
);
3382 /* handle typecasts */
3383 larg
= arg
->op
.left
;
3384 while (larg
->type
== PRINT_TYPE
) {
3387 larg
= larg
->typecast
.item
;
3390 /* Default to long size */
3391 field_size
= pevent
->long_size
;
3393 switch (larg
->type
) {
3394 case PRINT_DYNAMIC_ARRAY
:
3395 offset
= pevent_read_number(pevent
,
3396 data
+ larg
->dynarray
.field
->offset
,
3397 larg
->dynarray
.field
->size
);
3398 if (larg
->dynarray
.field
->elementsize
)
3399 field_size
= larg
->dynarray
.field
->elementsize
;
3401 * The actual length of the dynamic array is stored
3402 * in the top half of the field, and the offset
3403 * is in the bottom half of the 32 bit field.
3409 if (!larg
->field
.field
) {
3411 pevent_find_any_field(event
, larg
->field
.name
);
3412 if (!larg
->field
.field
) {
3414 goto out_warning_field
;
3417 field_size
= larg
->field
.field
->elementsize
;
3418 offset
= larg
->field
.field
->offset
+
3419 right
* larg
->field
.field
->elementsize
;
3422 goto default_op
; /* oops, all bets off */
3424 val
= pevent_read_number(pevent
,
3425 data
+ offset
, field_size
);
3427 val
= eval_type(val
, typearg
, 1);
3429 } else if (strcmp(arg
->op
.op
, "?") == 0) {
3430 left
= eval_num_arg(data
, size
, event
, arg
->op
.left
);
3431 arg
= arg
->op
.right
;
3433 val
= eval_num_arg(data
, size
, event
, arg
->op
.left
);
3435 val
= eval_num_arg(data
, size
, event
, arg
->op
.right
);
3439 left
= eval_num_arg(data
, size
, event
, arg
->op
.left
);
3440 right
= eval_num_arg(data
, size
, event
, arg
->op
.right
);
3441 switch (arg
->op
.op
[0]) {
3443 switch (arg
->op
.op
[1]) {
3448 val
= left
!= right
;
3451 goto out_warning_op
;
3459 val
= left
|| right
;
3465 val
= left
&& right
;
3470 switch (arg
->op
.op
[1]) {
3475 val
= left
<< right
;
3478 val
= left
<= right
;
3481 goto out_warning_op
;
3485 switch (arg
->op
.op
[1]) {
3490 val
= left
>> right
;
3493 val
= left
>= right
;
3496 goto out_warning_op
;
3500 if (arg
->op
.op
[1] != '=')
3501 goto out_warning_op
;
3503 val
= left
== right
;
3518 goto out_warning_op
;
3521 case PRINT_DYNAMIC_ARRAY
:
3522 /* Without [], we pass the address to the dynamic data */
3523 offset
= pevent_read_number(pevent
,
3524 data
+ arg
->dynarray
.field
->offset
,
3525 arg
->dynarray
.field
->size
);
3527 * The actual length of the dynamic array is stored
3528 * in the top half of the field, and the offset
3529 * is in the bottom half of the 32 bit field.
3532 val
= (unsigned long long)((unsigned long)data
+ offset
);
3534 default: /* not sure what to do there */
3540 do_warning_event(event
, "%s: unknown op '%s'", __func__
, arg
->op
.op
);
3544 do_warning_event(event
, "%s: field %s not found",
3545 __func__
, arg
->field
.name
);
3551 unsigned long long value
;
3554 static const struct flag flags
[] = {
3555 { "HI_SOFTIRQ", 0 },
3556 { "TIMER_SOFTIRQ", 1 },
3557 { "NET_TX_SOFTIRQ", 2 },
3558 { "NET_RX_SOFTIRQ", 3 },
3559 { "BLOCK_SOFTIRQ", 4 },
3560 { "BLOCK_IOPOLL_SOFTIRQ", 5 },
3561 { "TASKLET_SOFTIRQ", 6 },
3562 { "SCHED_SOFTIRQ", 7 },
3563 { "HRTIMER_SOFTIRQ", 8 },
3564 { "RCU_SOFTIRQ", 9 },
3566 { "HRTIMER_NORESTART", 0 },
3567 { "HRTIMER_RESTART", 1 },
3570 static unsigned long long eval_flag(const char *flag
)
3575 * Some flags in the format files do not get converted.
3576 * If the flag is not numeric, see if it is something that
3577 * we already know about.
3579 if (isdigit(flag
[0]))
3580 return strtoull(flag
, NULL
, 0);
3582 for (i
= 0; i
< (int)(sizeof(flags
)/sizeof(flags
[0])); i
++)
3583 if (strcmp(flags
[i
].name
, flag
) == 0)
3584 return flags
[i
].value
;
3589 static void print_str_to_seq(struct trace_seq
*s
, const char *format
,
3590 int len_arg
, const char *str
)
3593 trace_seq_printf(s
, format
, len_arg
, str
);
3595 trace_seq_printf(s
, format
, str
);
3598 static void print_bitmask_to_seq(struct pevent
*pevent
,
3599 struct trace_seq
*s
, const char *format
,
3600 int len_arg
, const void *data
, int size
)
3602 int nr_bits
= size
* 8;
3603 int str_size
= (nr_bits
+ 3) / 4;
3611 * The kernel likes to put in commas every 32 bits, we
3614 str_size
+= (nr_bits
- 1) / 32;
3616 str
= malloc(str_size
+ 1);
3618 do_warning("%s: not enough memory!", __func__
);
3623 /* Start out with -2 for the two chars per byte */
3624 for (i
= str_size
- 2; i
>= 0; i
-= 2) {
3626 * data points to a bit mask of size bytes.
3627 * In the kernel, this is an array of long words, thus
3628 * endianess is very important.
3630 if (pevent
->file_bigendian
)
3631 index
= size
- (len
+ 1);
3635 snprintf(buf
, 3, "%02x", *((unsigned char *)data
+ index
));
3636 memcpy(str
+ i
, buf
, 2);
3638 if (!(len
& 3) && i
> 0) {
3645 trace_seq_printf(s
, format
, len_arg
, str
);
3647 trace_seq_printf(s
, format
, str
);
3652 static void print_str_arg(struct trace_seq
*s
, void *data
, int size
,
3653 struct event_format
*event
, const char *format
,
3654 int len_arg
, struct print_arg
*arg
)
3656 struct pevent
*pevent
= event
->pevent
;
3657 struct print_flag_sym
*flag
;
3658 struct format_field
*field
;
3659 struct printk_map
*printk
;
3660 unsigned long long val
, fval
;
3667 switch (arg
->type
) {
3672 print_str_to_seq(s
, format
, len_arg
, arg
->atom
.atom
);
3675 field
= arg
->field
.field
;
3677 field
= pevent_find_any_field(event
, arg
->field
.name
);
3679 str
= arg
->field
.name
;
3680 goto out_warning_field
;
3682 arg
->field
.field
= field
;
3684 /* Zero sized fields, mean the rest of the data */
3685 len
= field
->size
? : size
- field
->offset
;
3688 * Some events pass in pointers. If this is not an array
3689 * and the size is the same as long_size, assume that it
3692 if (!(field
->flags
& FIELD_IS_ARRAY
) &&
3693 field
->size
== pevent
->long_size
) {
3694 addr
= *(unsigned long *)(data
+ field
->offset
);
3695 /* Check if it matches a print format */
3696 printk
= find_printk(pevent
, addr
);
3698 trace_seq_puts(s
, printk
->printk
);
3700 trace_seq_printf(s
, "%lx", addr
);
3703 str
= malloc(len
+ 1);
3705 do_warning_event(event
, "%s: not enough memory!",
3709 memcpy(str
, data
+ field
->offset
, len
);
3711 print_str_to_seq(s
, format
, len_arg
, str
);
3715 val
= eval_num_arg(data
, size
, event
, arg
->flags
.field
);
3717 for (flag
= arg
->flags
.flags
; flag
; flag
= flag
->next
) {
3718 fval
= eval_flag(flag
->value
);
3719 if (!val
&& !fval
) {
3720 print_str_to_seq(s
, format
, len_arg
, flag
->str
);
3723 if (fval
&& (val
& fval
) == fval
) {
3724 if (print
&& arg
->flags
.delim
)
3725 trace_seq_puts(s
, arg
->flags
.delim
);
3726 print_str_to_seq(s
, format
, len_arg
, flag
->str
);
3733 val
= eval_num_arg(data
, size
, event
, arg
->symbol
.field
);
3734 for (flag
= arg
->symbol
.symbols
; flag
; flag
= flag
->next
) {
3735 fval
= eval_flag(flag
->value
);
3737 print_str_to_seq(s
, format
, len_arg
, flag
->str
);
3743 if (arg
->hex
.field
->type
== PRINT_DYNAMIC_ARRAY
) {
3744 unsigned long offset
;
3745 offset
= pevent_read_number(pevent
,
3746 data
+ arg
->hex
.field
->dynarray
.field
->offset
,
3747 arg
->hex
.field
->dynarray
.field
->size
);
3748 hex
= data
+ (offset
& 0xffff);
3750 field
= arg
->hex
.field
->field
.field
;
3752 str
= arg
->hex
.field
->field
.name
;
3753 field
= pevent_find_any_field(event
, str
);
3755 goto out_warning_field
;
3756 arg
->hex
.field
->field
.field
= field
;
3758 hex
= data
+ field
->offset
;
3760 len
= eval_num_arg(data
, size
, event
, arg
->hex
.size
);
3761 for (i
= 0; i
< len
; i
++) {
3763 trace_seq_putc(s
, ' ');
3764 trace_seq_printf(s
, "%02x", hex
[i
]);
3770 case PRINT_STRING
: {
3773 if (arg
->string
.offset
== -1) {
3774 struct format_field
*f
;
3776 f
= pevent_find_any_field(event
, arg
->string
.string
);
3777 arg
->string
.offset
= f
->offset
;
3779 str_offset
= data2host4(pevent
, data
+ arg
->string
.offset
);
3780 str_offset
&= 0xffff;
3781 print_str_to_seq(s
, format
, len_arg
, ((char *)data
) + str_offset
);
3785 print_str_to_seq(s
, format
, len_arg
, arg
->string
.string
);
3787 case PRINT_BITMASK
: {
3791 if (arg
->bitmask
.offset
== -1) {
3792 struct format_field
*f
;
3794 f
= pevent_find_any_field(event
, arg
->bitmask
.bitmask
);
3795 arg
->bitmask
.offset
= f
->offset
;
3797 bitmask_offset
= data2host4(pevent
, data
+ arg
->bitmask
.offset
);
3798 bitmask_size
= bitmask_offset
>> 16;
3799 bitmask_offset
&= 0xffff;
3800 print_bitmask_to_seq(pevent
, s
, format
, len_arg
,
3801 data
+ bitmask_offset
, bitmask_size
);
3806 * The only op for string should be ? :
3808 if (arg
->op
.op
[0] != '?')
3810 val
= eval_num_arg(data
, size
, event
, arg
->op
.left
);
3812 print_str_arg(s
, data
, size
, event
,
3813 format
, len_arg
, arg
->op
.right
->op
.left
);
3815 print_str_arg(s
, data
, size
, event
,
3816 format
, len_arg
, arg
->op
.right
->op
.right
);
3819 process_defined_func(s
, data
, size
, event
, arg
);
3829 do_warning_event(event
, "%s: field %s not found",
3830 __func__
, arg
->field
.name
);
3833 static unsigned long long
3834 process_defined_func(struct trace_seq
*s
, void *data
, int size
,
3835 struct event_format
*event
, struct print_arg
*arg
)
3837 struct pevent_function_handler
*func_handle
= arg
->func
.func
;
3838 struct pevent_func_params
*param
;
3839 unsigned long long *args
;
3840 unsigned long long ret
;
3841 struct print_arg
*farg
;
3842 struct trace_seq str
;
3844 struct save_str
*next
;
3846 } *strings
= NULL
, *string
;
3849 if (!func_handle
->nr_args
) {
3850 ret
= (*func_handle
->func
)(s
, NULL
);
3854 farg
= arg
->func
.args
;
3855 param
= func_handle
->params
;
3858 args
= malloc(sizeof(*args
) * func_handle
->nr_args
);
3862 for (i
= 0; i
< func_handle
->nr_args
; i
++) {
3863 switch (param
->type
) {
3864 case PEVENT_FUNC_ARG_INT
:
3865 case PEVENT_FUNC_ARG_LONG
:
3866 case PEVENT_FUNC_ARG_PTR
:
3867 args
[i
] = eval_num_arg(data
, size
, event
, farg
);
3869 case PEVENT_FUNC_ARG_STRING
:
3870 trace_seq_init(&str
);
3871 print_str_arg(&str
, data
, size
, event
, "%s", -1, farg
);
3872 trace_seq_terminate(&str
);
3873 string
= malloc(sizeof(*string
));
3875 do_warning_event(event
, "%s(%d): malloc str",
3876 __func__
, __LINE__
);
3879 string
->next
= strings
;
3880 string
->str
= strdup(str
.buffer
);
3883 do_warning_event(event
, "%s(%d): malloc str",
3884 __func__
, __LINE__
);
3887 args
[i
] = (uintptr_t)string
->str
;
3889 trace_seq_destroy(&str
);
3893 * Something went totally wrong, this is not
3894 * an input error, something in this code broke.
3896 do_warning_event(event
, "Unexpected end of arguments\n");
3900 param
= param
->next
;
3903 ret
= (*func_handle
->func
)(s
, args
);
3908 strings
= string
->next
;
3914 /* TBD : handle return type here */
3918 static void free_args(struct print_arg
*args
)
3920 struct print_arg
*next
;
3930 static struct print_arg
*make_bprint_args(char *fmt
, void *data
, int size
, struct event_format
*event
)
3932 struct pevent
*pevent
= event
->pevent
;
3933 struct format_field
*field
, *ip_field
;
3934 struct print_arg
*args
, *arg
, **next
;
3935 unsigned long long ip
, val
;
3940 field
= pevent
->bprint_buf_field
;
3941 ip_field
= pevent
->bprint_ip_field
;
3944 field
= pevent_find_field(event
, "buf");
3946 do_warning_event(event
, "can't find buffer field for binary printk");
3949 ip_field
= pevent_find_field(event
, "ip");
3951 do_warning_event(event
, "can't find ip field for binary printk");
3954 pevent
->bprint_buf_field
= field
;
3955 pevent
->bprint_ip_field
= ip_field
;
3958 ip
= pevent_read_number(pevent
, data
+ ip_field
->offset
, ip_field
->size
);
3961 * The first arg is the IP pointer.
3965 do_warning_event(event
, "%s(%d): not enough memory!",
3966 __func__
, __LINE__
);
3973 arg
->type
= PRINT_ATOM
;
3975 if (asprintf(&arg
->atom
.atom
, "%lld", ip
) < 0)
3978 /* skip the first "%pf: " */
3979 for (ptr
= fmt
+ 5, bptr
= data
+ field
->offset
;
3980 bptr
< data
+ size
&& *ptr
; ptr
++) {
4011 vsize
= pevent
->long_size
;
4025 /* the pointers are always 4 bytes aligned */
4026 bptr
= (void *)(((unsigned long)bptr
+ 3) &
4028 val
= pevent_read_number(pevent
, bptr
, vsize
);
4032 do_warning_event(event
, "%s(%d): not enough memory!",
4033 __func__
, __LINE__
);
4037 arg
->type
= PRINT_ATOM
;
4038 if (asprintf(&arg
->atom
.atom
, "%lld", val
) < 0) {
4045 * The '*' case means that an arg is used as the length.
4046 * We need to continue to figure out for what.
4055 do_warning_event(event
, "%s(%d): not enough memory!",
4056 __func__
, __LINE__
);
4060 arg
->type
= PRINT_BSTRING
;
4061 arg
->string
.string
= strdup(bptr
);
4062 if (!arg
->string
.string
)
4064 bptr
+= strlen(bptr
) + 1;
4081 get_bprint_format(void *data
, int size __maybe_unused
,
4082 struct event_format
*event
)
4084 struct pevent
*pevent
= event
->pevent
;
4085 unsigned long long addr
;
4086 struct format_field
*field
;
4087 struct printk_map
*printk
;
4090 field
= pevent
->bprint_fmt_field
;
4093 field
= pevent_find_field(event
, "fmt");
4095 do_warning_event(event
, "can't find format field for binary printk");
4098 pevent
->bprint_fmt_field
= field
;
4101 addr
= pevent_read_number(pevent
, data
+ field
->offset
, field
->size
);
4103 printk
= find_printk(pevent
, addr
);
4105 if (asprintf(&format
, "%%pf: (NO FORMAT FOUND at %llx)\n", addr
) < 0)
4110 if (asprintf(&format
, "%s: %s", "%pf", printk
->printk
) < 0)
4116 static void print_mac_arg(struct trace_seq
*s
, int mac
, void *data
, int size
,
4117 struct event_format
*event
, struct print_arg
*arg
)
4120 const char *fmt
= "%.2x:%.2x:%.2x:%.2x:%.2x:%.2x";
4122 if (arg
->type
== PRINT_FUNC
) {
4123 process_defined_func(s
, data
, size
, event
, arg
);
4127 if (arg
->type
!= PRINT_FIELD
) {
4128 trace_seq_printf(s
, "ARG TYPE NOT FIELD BUT %d",
4134 fmt
= "%.2x%.2x%.2x%.2x%.2x%.2x";
4135 if (!arg
->field
.field
) {
4137 pevent_find_any_field(event
, arg
->field
.name
);
4138 if (!arg
->field
.field
) {
4139 do_warning_event(event
, "%s: field %s not found",
4140 __func__
, arg
->field
.name
);
4144 if (arg
->field
.field
->size
!= 6) {
4145 trace_seq_printf(s
, "INVALIDMAC");
4148 buf
= data
+ arg
->field
.field
->offset
;
4149 trace_seq_printf(s
, fmt
, buf
[0], buf
[1], buf
[2], buf
[3], buf
[4], buf
[5]);
4152 static int is_printable_array(char *p
, unsigned int len
)
4156 for (i
= 0; i
< len
&& p
[i
]; i
++)
4157 if (!isprint(p
[i
]) && !isspace(p
[i
]))
4162 static void print_event_fields(struct trace_seq
*s
, void *data
,
4163 int size __maybe_unused
,
4164 struct event_format
*event
)
4166 struct format_field
*field
;
4167 unsigned long long val
;
4168 unsigned int offset
, len
, i
;
4170 field
= event
->format
.fields
;
4172 trace_seq_printf(s
, " %s=", field
->name
);
4173 if (field
->flags
& FIELD_IS_ARRAY
) {
4174 offset
= field
->offset
;
4176 if (field
->flags
& FIELD_IS_DYNAMIC
) {
4177 val
= pevent_read_number(event
->pevent
, data
+ offset
, len
);
4182 if (field
->flags
& FIELD_IS_STRING
&&
4183 is_printable_array(data
+ offset
, len
)) {
4184 trace_seq_printf(s
, "%s", (char *)data
+ offset
);
4186 trace_seq_puts(s
, "ARRAY[");
4187 for (i
= 0; i
< len
; i
++) {
4189 trace_seq_puts(s
, ", ");
4190 trace_seq_printf(s
, "%02x",
4191 *((unsigned char *)data
+ offset
+ i
));
4193 trace_seq_putc(s
, ']');
4194 field
->flags
&= ~FIELD_IS_STRING
;
4197 val
= pevent_read_number(event
->pevent
, data
+ field
->offset
,
4199 if (field
->flags
& FIELD_IS_POINTER
) {
4200 trace_seq_printf(s
, "0x%llx", val
);
4201 } else if (field
->flags
& FIELD_IS_SIGNED
) {
4202 switch (field
->size
) {
4205 * If field is long then print it in hex.
4206 * A long usually stores pointers.
4208 if (field
->flags
& FIELD_IS_LONG
)
4209 trace_seq_printf(s
, "0x%x", (int)val
);
4211 trace_seq_printf(s
, "%d", (int)val
);
4214 trace_seq_printf(s
, "%2d", (short)val
);
4217 trace_seq_printf(s
, "%1d", (char)val
);
4220 trace_seq_printf(s
, "%lld", val
);
4223 if (field
->flags
& FIELD_IS_LONG
)
4224 trace_seq_printf(s
, "0x%llx", val
);
4226 trace_seq_printf(s
, "%llu", val
);
4229 field
= field
->next
;
4233 static void pretty_print(struct trace_seq
*s
, void *data
, int size
, struct event_format
*event
)
4235 struct pevent
*pevent
= event
->pevent
;
4236 struct print_fmt
*print_fmt
= &event
->print_fmt
;
4237 struct print_arg
*arg
= print_fmt
->args
;
4238 struct print_arg
*args
= NULL
;
4239 const char *ptr
= print_fmt
->format
;
4240 unsigned long long val
;
4241 struct func_map
*func
;
4242 const char *saveptr
;
4244 char *bprint_fmt
= NULL
;
4252 if (event
->flags
& EVENT_FL_FAILED
) {
4253 trace_seq_printf(s
, "[FAILED TO PARSE]");
4254 print_event_fields(s
, data
, size
, event
);
4258 if (event
->flags
& EVENT_FL_ISBPRINT
) {
4259 bprint_fmt
= get_bprint_format(data
, size
, event
);
4260 args
= make_bprint_args(bprint_fmt
, data
, size
, event
);
4265 for (; *ptr
; ptr
++) {
4271 trace_seq_putc(s
, '\n');
4274 trace_seq_putc(s
, '\t');
4277 trace_seq_putc(s
, '\r');
4280 trace_seq_putc(s
, '\\');
4283 trace_seq_putc(s
, *ptr
);
4287 } else if (*ptr
== '%') {
4295 trace_seq_putc(s
, '%');
4298 /* FIXME: need to handle properly */
4310 /* The argument is the length. */
4312 do_warning_event(event
, "no argument match");
4313 event
->flags
|= EVENT_FL_FAILED
;
4316 len_arg
= eval_num_arg(data
, size
, event
, arg
);
4326 if (pevent
->long_size
== 4)
4331 if (*(ptr
+1) == 'F' ||
4335 } else if (*(ptr
+1) == 'M' || *(ptr
+1) == 'm') {
4336 print_mac_arg(s
, *(ptr
+1), data
, size
, event
, arg
);
4349 do_warning_event(event
, "no argument match");
4350 event
->flags
|= EVENT_FL_FAILED
;
4354 len
= ((unsigned long)ptr
+ 1) -
4355 (unsigned long)saveptr
;
4357 /* should never happen */
4359 do_warning_event(event
, "bad format!");
4360 event
->flags
|= EVENT_FL_FAILED
;
4364 memcpy(format
, saveptr
, len
);
4367 val
= eval_num_arg(data
, size
, event
, arg
);
4371 func
= find_func(pevent
, val
);
4373 trace_seq_puts(s
, func
->func
);
4374 if (show_func
== 'F')
4381 if (pevent
->long_size
== 8 && ls
&&
4382 sizeof(long) != 8) {
4386 /* make %l into %ll */
4387 p
= strchr(format
, 'l');
4389 memmove(p
+1, p
, strlen(p
)+1);
4390 else if (strcmp(format
, "%p") == 0)
4391 strcpy(format
, "0x%llx");
4396 trace_seq_printf(s
, format
, len_arg
, (char)val
);
4398 trace_seq_printf(s
, format
, (char)val
);
4402 trace_seq_printf(s
, format
, len_arg
, (short)val
);
4404 trace_seq_printf(s
, format
, (short)val
);
4408 trace_seq_printf(s
, format
, len_arg
, (int)val
);
4410 trace_seq_printf(s
, format
, (int)val
);
4414 trace_seq_printf(s
, format
, len_arg
, (long)val
);
4416 trace_seq_printf(s
, format
, (long)val
);
4420 trace_seq_printf(s
, format
, len_arg
,
4423 trace_seq_printf(s
, format
, (long long)val
);
4426 do_warning_event(event
, "bad count (%d)", ls
);
4427 event
->flags
|= EVENT_FL_FAILED
;
4432 do_warning_event(event
, "no matching argument");
4433 event
->flags
|= EVENT_FL_FAILED
;
4437 len
= ((unsigned long)ptr
+ 1) -
4438 (unsigned long)saveptr
;
4440 /* should never happen */
4442 do_warning_event(event
, "bad format!");
4443 event
->flags
|= EVENT_FL_FAILED
;
4447 memcpy(format
, saveptr
, len
);
4451 /* Use helper trace_seq */
4453 print_str_arg(&p
, data
, size
, event
,
4454 format
, len_arg
, arg
);
4455 trace_seq_terminate(&p
);
4456 trace_seq_puts(s
, p
.buffer
);
4457 trace_seq_destroy(&p
);
4461 trace_seq_printf(s
, ">%c<", *ptr
);
4465 trace_seq_putc(s
, *ptr
);
4468 if (event
->flags
& EVENT_FL_FAILED
) {
4470 trace_seq_printf(s
, "[FAILED TO PARSE]");
4480 * pevent_data_lat_fmt - parse the data for the latency format
4481 * @pevent: a handle to the pevent
4482 * @s: the trace_seq to write to
4483 * @record: the record to read from
4485 * This parses out the Latency format (interrupts disabled,
4486 * need rescheduling, in hard/soft interrupt, preempt count
4487 * and lock depth) and places it into the trace_seq.
4489 void pevent_data_lat_fmt(struct pevent
*pevent
,
4490 struct trace_seq
*s
, struct pevent_record
*record
)
4492 static int check_lock_depth
= 1;
4493 static int check_migrate_disable
= 1;
4494 static int lock_depth_exists
;
4495 static int migrate_disable_exists
;
4496 unsigned int lat_flags
;
4499 int migrate_disable
;
4502 void *data
= record
->data
;
4504 lat_flags
= parse_common_flags(pevent
, data
);
4505 pc
= parse_common_pc(pevent
, data
);
4506 /* lock_depth may not always exist */
4507 if (lock_depth_exists
)
4508 lock_depth
= parse_common_lock_depth(pevent
, data
);
4509 else if (check_lock_depth
) {
4510 lock_depth
= parse_common_lock_depth(pevent
, data
);
4512 check_lock_depth
= 0;
4514 lock_depth_exists
= 1;
4517 /* migrate_disable may not always exist */
4518 if (migrate_disable_exists
)
4519 migrate_disable
= parse_common_migrate_disable(pevent
, data
);
4520 else if (check_migrate_disable
) {
4521 migrate_disable
= parse_common_migrate_disable(pevent
, data
);
4522 if (migrate_disable
< 0)
4523 check_migrate_disable
= 0;
4525 migrate_disable_exists
= 1;
4528 hardirq
= lat_flags
& TRACE_FLAG_HARDIRQ
;
4529 softirq
= lat_flags
& TRACE_FLAG_SOFTIRQ
;
4531 trace_seq_printf(s
, "%c%c%c",
4532 (lat_flags
& TRACE_FLAG_IRQS_OFF
) ? 'd' :
4533 (lat_flags
& TRACE_FLAG_IRQS_NOSUPPORT
) ?
4535 (lat_flags
& TRACE_FLAG_NEED_RESCHED
) ?
4537 (hardirq
&& softirq
) ? 'H' :
4538 hardirq
? 'h' : softirq
? 's' : '.');
4541 trace_seq_printf(s
, "%x", pc
);
4543 trace_seq_putc(s
, '.');
4545 if (migrate_disable_exists
) {
4546 if (migrate_disable
< 0)
4547 trace_seq_putc(s
, '.');
4549 trace_seq_printf(s
, "%d", migrate_disable
);
4552 if (lock_depth_exists
) {
4554 trace_seq_putc(s
, '.');
4556 trace_seq_printf(s
, "%d", lock_depth
);
4559 trace_seq_terminate(s
);
4563 * pevent_data_type - parse out the given event type
4564 * @pevent: a handle to the pevent
4565 * @rec: the record to read from
4567 * This returns the event id from the @rec.
4569 int pevent_data_type(struct pevent
*pevent
, struct pevent_record
*rec
)
4571 return trace_parse_common_type(pevent
, rec
->data
);
4575 * pevent_data_event_from_type - find the event by a given type
4576 * @pevent: a handle to the pevent
4577 * @type: the type of the event.
4579 * This returns the event form a given @type;
4581 struct event_format
*pevent_data_event_from_type(struct pevent
*pevent
, int type
)
4583 return pevent_find_event(pevent
, type
);
4587 * pevent_data_pid - parse the PID from raw data
4588 * @pevent: a handle to the pevent
4589 * @rec: the record to parse
4591 * This returns the PID from a raw data.
4593 int pevent_data_pid(struct pevent
*pevent
, struct pevent_record
*rec
)
4595 return parse_common_pid(pevent
, rec
->data
);
4599 * pevent_data_comm_from_pid - return the command line from PID
4600 * @pevent: a handle to the pevent
4601 * @pid: the PID of the task to search for
4603 * This returns a pointer to the command line that has the given
4606 const char *pevent_data_comm_from_pid(struct pevent
*pevent
, int pid
)
4610 comm
= find_cmdline(pevent
, pid
);
4615 * pevent_data_comm_from_pid - parse the data into the print format
4616 * @s: the trace_seq to write to
4617 * @event: the handle to the event
4618 * @record: the record to read from
4620 * This parses the raw @data using the given @event information and
4621 * writes the print format into the trace_seq.
4623 void pevent_event_info(struct trace_seq
*s
, struct event_format
*event
,
4624 struct pevent_record
*record
)
4626 int print_pretty
= 1;
4628 if (event
->pevent
->print_raw
|| (event
->flags
& EVENT_FL_PRINTRAW
))
4629 print_event_fields(s
, record
->data
, record
->size
, event
);
4632 if (event
->handler
&& !(event
->flags
& EVENT_FL_NOHANDLE
))
4633 print_pretty
= event
->handler(s
, record
, event
,
4637 pretty_print(s
, record
->data
, record
->size
, event
);
4640 trace_seq_terminate(s
);
4643 static bool is_timestamp_in_us(char *trace_clock
, bool use_trace_clock
)
4645 if (!use_trace_clock
)
4648 if (!strcmp(trace_clock
, "local") || !strcmp(trace_clock
, "global")
4649 || !strcmp(trace_clock
, "uptime") || !strcmp(trace_clock
, "perf"))
4652 /* trace_clock is setting in tsc or counter mode */
4656 void pevent_print_event(struct pevent
*pevent
, struct trace_seq
*s
,
4657 struct pevent_record
*record
, bool use_trace_clock
)
4659 static const char *spaces
= " "; /* 20 spaces */
4660 struct event_format
*event
;
4662 unsigned long usecs
;
4663 unsigned long nsecs
;
4665 void *data
= record
->data
;
4670 bool use_usec_format
;
4672 use_usec_format
= is_timestamp_in_us(pevent
->trace_clock
,
4674 if (use_usec_format
) {
4675 secs
= record
->ts
/ NSECS_PER_SEC
;
4676 nsecs
= record
->ts
- secs
* NSECS_PER_SEC
;
4679 if (record
->size
< 0) {
4680 do_warning("ug! negative record size %d", record
->size
);
4684 type
= trace_parse_common_type(pevent
, data
);
4686 event
= pevent_find_event(pevent
, type
);
4688 do_warning("ug! no event found for type %d", type
);
4692 pid
= parse_common_pid(pevent
, data
);
4693 comm
= find_cmdline(pevent
, pid
);
4695 if (pevent
->latency_format
) {
4696 trace_seq_printf(s
, "%8.8s-%-5d %3d",
4697 comm
, pid
, record
->cpu
);
4698 pevent_data_lat_fmt(pevent
, s
, record
);
4700 trace_seq_printf(s
, "%16s-%-5d [%03d]", comm
, pid
, record
->cpu
);
4702 if (use_usec_format
) {
4703 if (pevent
->flags
& PEVENT_NSEC_OUTPUT
) {
4707 usecs
= (nsecs
+ 500) / NSECS_PER_USEC
;
4711 trace_seq_printf(s
, " %5lu.%0*lu: %s: ",
4712 secs
, p
, usecs
, event
->name
);
4714 trace_seq_printf(s
, " %12llu: %s: ",
4715 record
->ts
, event
->name
);
4717 /* Space out the event names evenly. */
4718 len
= strlen(event
->name
);
4720 trace_seq_printf(s
, "%.*s", 20 - len
, spaces
);
4722 pevent_event_info(s
, event
, record
);
4725 static int events_id_cmp(const void *a
, const void *b
)
4727 struct event_format
* const * ea
= a
;
4728 struct event_format
* const * eb
= b
;
4730 if ((*ea
)->id
< (*eb
)->id
)
4733 if ((*ea
)->id
> (*eb
)->id
)
4739 static int events_name_cmp(const void *a
, const void *b
)
4741 struct event_format
* const * ea
= a
;
4742 struct event_format
* const * eb
= b
;
4745 res
= strcmp((*ea
)->name
, (*eb
)->name
);
4749 res
= strcmp((*ea
)->system
, (*eb
)->system
);
4753 return events_id_cmp(a
, b
);
4756 static int events_system_cmp(const void *a
, const void *b
)
4758 struct event_format
* const * ea
= a
;
4759 struct event_format
* const * eb
= b
;
4762 res
= strcmp((*ea
)->system
, (*eb
)->system
);
4766 res
= strcmp((*ea
)->name
, (*eb
)->name
);
4770 return events_id_cmp(a
, b
);
4773 struct event_format
**pevent_list_events(struct pevent
*pevent
, enum event_sort_type sort_type
)
4775 struct event_format
**events
;
4776 int (*sort
)(const void *a
, const void *b
);
4778 events
= pevent
->sort_events
;
4780 if (events
&& pevent
->last_type
== sort_type
)
4784 events
= malloc(sizeof(*events
) * (pevent
->nr_events
+ 1));
4788 memcpy(events
, pevent
->events
, sizeof(*events
) * pevent
->nr_events
);
4789 events
[pevent
->nr_events
] = NULL
;
4791 pevent
->sort_events
= events
;
4793 /* the internal events are sorted by id */
4794 if (sort_type
== EVENT_SORT_ID
) {
4795 pevent
->last_type
= sort_type
;
4800 switch (sort_type
) {
4802 sort
= events_id_cmp
;
4804 case EVENT_SORT_NAME
:
4805 sort
= events_name_cmp
;
4807 case EVENT_SORT_SYSTEM
:
4808 sort
= events_system_cmp
;
4814 qsort(events
, pevent
->nr_events
, sizeof(*events
), sort
);
4815 pevent
->last_type
= sort_type
;
4820 static struct format_field
**
4821 get_event_fields(const char *type
, const char *name
,
4822 int count
, struct format_field
*list
)
4824 struct format_field
**fields
;
4825 struct format_field
*field
;
4828 fields
= malloc(sizeof(*fields
) * (count
+ 1));
4832 for (field
= list
; field
; field
= field
->next
) {
4833 fields
[i
++] = field
;
4834 if (i
== count
+ 1) {
4835 do_warning("event %s has more %s fields than specified",
4843 do_warning("event %s has less %s fields than specified",
4852 * pevent_event_common_fields - return a list of common fields for an event
4853 * @event: the event to return the common fields of.
4855 * Returns an allocated array of fields. The last item in the array is NULL.
4856 * The array must be freed with free().
4858 struct format_field
**pevent_event_common_fields(struct event_format
*event
)
4860 return get_event_fields("common", event
->name
,
4861 event
->format
.nr_common
,
4862 event
->format
.common_fields
);
4866 * pevent_event_fields - return a list of event specific fields for an event
4867 * @event: the event to return the fields of.
4869 * Returns an allocated array of fields. The last item in the array is NULL.
4870 * The array must be freed with free().
4872 struct format_field
**pevent_event_fields(struct event_format
*event
)
4874 return get_event_fields("event", event
->name
,
4875 event
->format
.nr_fields
,
4876 event
->format
.fields
);
4879 static void print_fields(struct trace_seq
*s
, struct print_flag_sym
*field
)
4881 trace_seq_printf(s
, "{ %s, %s }", field
->value
, field
->str
);
4883 trace_seq_puts(s
, ", ");
4884 print_fields(s
, field
->next
);
4889 static void print_args(struct print_arg
*args
)
4891 int print_paren
= 1;
4894 switch (args
->type
) {
4899 printf("%s", args
->atom
.atom
);
4902 printf("REC->%s", args
->field
.name
);
4905 printf("__print_flags(");
4906 print_args(args
->flags
.field
);
4907 printf(", %s, ", args
->flags
.delim
);
4909 print_fields(&s
, args
->flags
.flags
);
4910 trace_seq_do_printf(&s
);
4911 trace_seq_destroy(&s
);
4915 printf("__print_symbolic(");
4916 print_args(args
->symbol
.field
);
4919 print_fields(&s
, args
->symbol
.symbols
);
4920 trace_seq_do_printf(&s
);
4921 trace_seq_destroy(&s
);
4925 printf("__print_hex(");
4926 print_args(args
->hex
.field
);
4928 print_args(args
->hex
.size
);
4933 printf("__get_str(%s)", args
->string
.string
);
4936 printf("__get_bitmask(%s)", args
->bitmask
.bitmask
);
4939 printf("(%s)", args
->typecast
.type
);
4940 print_args(args
->typecast
.item
);
4943 if (strcmp(args
->op
.op
, ":") == 0)
4947 print_args(args
->op
.left
);
4948 printf(" %s ", args
->op
.op
);
4949 print_args(args
->op
.right
);
4954 /* we should warn... */
4959 print_args(args
->next
);
4963 static void parse_header_field(const char *field
,
4964 int *offset
, int *size
, int mandatory
)
4966 unsigned long long save_input_buf_ptr
;
4967 unsigned long long save_input_buf_siz
;
4971 save_input_buf_ptr
= input_buf_ptr
;
4972 save_input_buf_siz
= input_buf_siz
;
4974 if (read_expected(EVENT_ITEM
, "field") < 0)
4976 if (read_expected(EVENT_OP
, ":") < 0)
4980 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
4985 * If this is not a mandatory field, then test it first.
4988 if (read_expected(EVENT_ITEM
, field
) < 0)
4991 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
4993 if (strcmp(token
, field
) != 0)
4998 if (read_expected(EVENT_OP
, ";") < 0)
5000 if (read_expected(EVENT_ITEM
, "offset") < 0)
5002 if (read_expected(EVENT_OP
, ":") < 0)
5004 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
5006 *offset
= atoi(token
);
5008 if (read_expected(EVENT_OP
, ";") < 0)
5010 if (read_expected(EVENT_ITEM
, "size") < 0)
5012 if (read_expected(EVENT_OP
, ":") < 0)
5014 if (read_expect_type(EVENT_ITEM
, &token
) < 0)
5016 *size
= atoi(token
);
5018 if (read_expected(EVENT_OP
, ";") < 0)
5020 type
= read_token(&token
);
5021 if (type
!= EVENT_NEWLINE
) {
5022 /* newer versions of the kernel have a "signed" type */
5023 if (type
!= EVENT_ITEM
)
5026 if (strcmp(token
, "signed") != 0)
5031 if (read_expected(EVENT_OP
, ":") < 0)
5034 if (read_expect_type(EVENT_ITEM
, &token
))
5038 if (read_expected(EVENT_OP
, ";") < 0)
5041 if (read_expect_type(EVENT_NEWLINE
, &token
))
5049 input_buf_ptr
= save_input_buf_ptr
;
5050 input_buf_siz
= save_input_buf_siz
;
5057 * pevent_parse_header_page - parse the data stored in the header page
5058 * @pevent: the handle to the pevent
5059 * @buf: the buffer storing the header page format string
5060 * @size: the size of @buf
5061 * @long_size: the long size to use if there is no header
5063 * This parses the header page format for information on the
5064 * ring buffer used. The @buf should be copied from
5066 * /sys/kernel/debug/tracing/events/header_page
5068 int pevent_parse_header_page(struct pevent
*pevent
, char *buf
, unsigned long size
,
5075 * Old kernels did not have header page info.
5076 * Sorry but we just use what we find here in user space.
5078 pevent
->header_page_ts_size
= sizeof(long long);
5079 pevent
->header_page_size_size
= long_size
;
5080 pevent
->header_page_data_offset
= sizeof(long long) + long_size
;
5081 pevent
->old_format
= 1;
5084 init_input_buf(buf
, size
);
5086 parse_header_field("timestamp", &pevent
->header_page_ts_offset
,
5087 &pevent
->header_page_ts_size
, 1);
5088 parse_header_field("commit", &pevent
->header_page_size_offset
,
5089 &pevent
->header_page_size_size
, 1);
5090 parse_header_field("overwrite", &pevent
->header_page_overwrite
,
5092 parse_header_field("data", &pevent
->header_page_data_offset
,
5093 &pevent
->header_page_data_size
, 1);
5098 static int event_matches(struct event_format
*event
,
5099 int id
, const char *sys_name
,
5100 const char *event_name
)
5102 if (id
>= 0 && id
!= event
->id
)
5105 if (event_name
&& (strcmp(event_name
, event
->name
) != 0))
5108 if (sys_name
&& (strcmp(sys_name
, event
->system
) != 0))
5114 static void free_handler(struct event_handler
*handle
)
5116 free((void *)handle
->sys_name
);
5117 free((void *)handle
->event_name
);
5121 static int find_event_handle(struct pevent
*pevent
, struct event_format
*event
)
5123 struct event_handler
*handle
, **next
;
5125 for (next
= &pevent
->handlers
; *next
;
5126 next
= &(*next
)->next
) {
5128 if (event_matches(event
, handle
->id
,
5130 handle
->event_name
))
5137 pr_stat("overriding event (%d) %s:%s with new print handler",
5138 event
->id
, event
->system
, event
->name
);
5140 event
->handler
= handle
->func
;
5141 event
->context
= handle
->context
;
5143 *next
= handle
->next
;
5144 free_handler(handle
);
5150 * __pevent_parse_format - parse the event format
5151 * @buf: the buffer storing the event format string
5152 * @size: the size of @buf
5153 * @sys: the system the event belongs to
5155 * This parses the event format and creates an event structure
5156 * to quickly parse raw data for a given event.
5158 * These files currently come from:
5160 * /sys/kernel/debug/tracing/events/.../.../format
5162 enum pevent_errno
__pevent_parse_format(struct event_format
**eventp
,
5163 struct pevent
*pevent
, const char *buf
,
5164 unsigned long size
, const char *sys
)
5166 struct event_format
*event
;
5169 init_input_buf(buf
, size
);
5171 *eventp
= event
= alloc_event();
5173 return PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5175 event
->name
= event_read_name();
5178 ret
= PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5179 goto event_alloc_failed
;
5182 if (strcmp(sys
, "ftrace") == 0) {
5183 event
->flags
|= EVENT_FL_ISFTRACE
;
5185 if (strcmp(event
->name
, "bprint") == 0)
5186 event
->flags
|= EVENT_FL_ISBPRINT
;
5189 event
->id
= event_read_id();
5190 if (event
->id
< 0) {
5191 ret
= PEVENT_ERRNO__READ_ID_FAILED
;
5193 * This isn't an allocation error actually.
5194 * But as the ID is critical, just bail out.
5196 goto event_alloc_failed
;
5199 event
->system
= strdup(sys
);
5200 if (!event
->system
) {
5201 ret
= PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5202 goto event_alloc_failed
;
5205 /* Add pevent to event so that it can be referenced */
5206 event
->pevent
= pevent
;
5208 ret
= event_read_format(event
);
5210 ret
= PEVENT_ERRNO__READ_FORMAT_FAILED
;
5211 goto event_parse_failed
;
5215 * If the event has an override, don't print warnings if the event
5216 * print format fails to parse.
5218 if (pevent
&& find_event_handle(pevent
, event
))
5221 ret
= event_read_print(event
);
5225 ret
= PEVENT_ERRNO__READ_PRINT_FAILED
;
5226 goto event_parse_failed
;
5229 if (!ret
&& (event
->flags
& EVENT_FL_ISFTRACE
)) {
5230 struct format_field
*field
;
5231 struct print_arg
*arg
, **list
;
5233 /* old ftrace had no args */
5234 list
= &event
->print_fmt
.args
;
5235 for (field
= event
->format
.fields
; field
; field
= field
->next
) {
5238 event
->flags
|= EVENT_FL_FAILED
;
5239 return PEVENT_ERRNO__OLD_FTRACE_ARG_FAILED
;
5241 arg
->type
= PRINT_FIELD
;
5242 arg
->field
.name
= strdup(field
->name
);
5243 if (!arg
->field
.name
) {
5244 event
->flags
|= EVENT_FL_FAILED
;
5246 return PEVENT_ERRNO__OLD_FTRACE_ARG_FAILED
;
5248 arg
->field
.field
= field
;
5258 event
->flags
|= EVENT_FL_FAILED
;
5262 free(event
->system
);
5269 static enum pevent_errno
5270 __pevent_parse_event(struct pevent
*pevent
,
5271 struct event_format
**eventp
,
5272 const char *buf
, unsigned long size
,
5275 int ret
= __pevent_parse_format(eventp
, pevent
, buf
, size
, sys
);
5276 struct event_format
*event
= *eventp
;
5281 if (pevent
&& add_event(pevent
, event
)) {
5282 ret
= PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5283 goto event_add_failed
;
5286 #define PRINT_ARGS 0
5287 if (PRINT_ARGS
&& event
->print_fmt
.args
)
5288 print_args(event
->print_fmt
.args
);
5293 pevent_free_format(event
);
5298 * pevent_parse_format - parse the event format
5299 * @pevent: the handle to the pevent
5300 * @eventp: returned format
5301 * @buf: the buffer storing the event format string
5302 * @size: the size of @buf
5303 * @sys: the system the event belongs to
5305 * This parses the event format and creates an event structure
5306 * to quickly parse raw data for a given event.
5308 * These files currently come from:
5310 * /sys/kernel/debug/tracing/events/.../.../format
5312 enum pevent_errno
pevent_parse_format(struct pevent
*pevent
,
5313 struct event_format
**eventp
,
5315 unsigned long size
, const char *sys
)
5317 return __pevent_parse_event(pevent
, eventp
, buf
, size
, sys
);
5321 * pevent_parse_event - parse the event format
5322 * @pevent: the handle to the pevent
5323 * @buf: the buffer storing the event format string
5324 * @size: the size of @buf
5325 * @sys: the system the event belongs to
5327 * This parses the event format and creates an event structure
5328 * to quickly parse raw data for a given event.
5330 * These files currently come from:
5332 * /sys/kernel/debug/tracing/events/.../.../format
5334 enum pevent_errno
pevent_parse_event(struct pevent
*pevent
, const char *buf
,
5335 unsigned long size
, const char *sys
)
5337 struct event_format
*event
= NULL
;
5338 return __pevent_parse_event(pevent
, &event
, buf
, size
, sys
);
5342 #define _PE(code, str) str
5343 static const char * const pevent_error_str
[] = {
5348 int pevent_strerror(struct pevent
*pevent __maybe_unused
,
5349 enum pevent_errno errnum
, char *buf
, size_t buflen
)
5355 msg
= strerror_r(errnum
, buf
, buflen
);
5357 size_t len
= strlen(msg
);
5358 memcpy(buf
, msg
, min(buflen
- 1, len
));
5359 *(buf
+ min(buflen
- 1, len
)) = '\0';
5364 if (errnum
<= __PEVENT_ERRNO__START
||
5365 errnum
>= __PEVENT_ERRNO__END
)
5368 idx
= errnum
- __PEVENT_ERRNO__START
- 1;
5369 msg
= pevent_error_str
[idx
];
5370 snprintf(buf
, buflen
, "%s", msg
);
5375 int get_field_val(struct trace_seq
*s
, struct format_field
*field
,
5376 const char *name
, struct pevent_record
*record
,
5377 unsigned long long *val
, int err
)
5381 trace_seq_printf(s
, "<CANT FIND FIELD %s>", name
);
5385 if (pevent_read_number_field(field
, record
->data
, val
)) {
5387 trace_seq_printf(s
, " %s=INVALID", name
);
5395 * pevent_get_field_raw - return the raw pointer into the data field
5396 * @s: The seq to print to on error
5397 * @event: the event that the field is for
5398 * @name: The name of the field
5399 * @record: The record with the field name.
5400 * @len: place to store the field length.
5401 * @err: print default error if failed.
5403 * Returns a pointer into record->data of the field and places
5404 * the length of the field in @len.
5406 * On failure, it returns NULL.
5408 void *pevent_get_field_raw(struct trace_seq
*s
, struct event_format
*event
,
5409 const char *name
, struct pevent_record
*record
,
5412 struct format_field
*field
;
5413 void *data
= record
->data
;
5420 field
= pevent_find_field(event
, name
);
5424 trace_seq_printf(s
, "<CANT FIND FIELD %s>", name
);
5428 /* Allow @len to be NULL */
5432 offset
= field
->offset
;
5433 if (field
->flags
& FIELD_IS_DYNAMIC
) {
5434 offset
= pevent_read_number(event
->pevent
,
5435 data
+ offset
, field
->size
);
5436 *len
= offset
>> 16;
5441 return data
+ offset
;
5445 * pevent_get_field_val - find a field and return its value
5446 * @s: The seq to print to on error
5447 * @event: the event that the field is for
5448 * @name: The name of the field
5449 * @record: The record with the field name.
5450 * @val: place to store the value of the field.
5451 * @err: print default error if failed.
5453 * Returns 0 on success -1 on field not found.
5455 int pevent_get_field_val(struct trace_seq
*s
, struct event_format
*event
,
5456 const char *name
, struct pevent_record
*record
,
5457 unsigned long long *val
, int err
)
5459 struct format_field
*field
;
5464 field
= pevent_find_field(event
, name
);
5466 return get_field_val(s
, field
, name
, record
, val
, err
);
5470 * pevent_get_common_field_val - find a common field and return its value
5471 * @s: The seq to print to on error
5472 * @event: the event that the field is for
5473 * @name: The name of the field
5474 * @record: The record with the field name.
5475 * @val: place to store the value of the field.
5476 * @err: print default error if failed.
5478 * Returns 0 on success -1 on field not found.
5480 int pevent_get_common_field_val(struct trace_seq
*s
, struct event_format
*event
,
5481 const char *name
, struct pevent_record
*record
,
5482 unsigned long long *val
, int err
)
5484 struct format_field
*field
;
5489 field
= pevent_find_common_field(event
, name
);
5491 return get_field_val(s
, field
, name
, record
, val
, err
);
5495 * pevent_get_any_field_val - find a any field and return its value
5496 * @s: The seq to print to on error
5497 * @event: the event that the field is for
5498 * @name: The name of the field
5499 * @record: The record with the field name.
5500 * @val: place to store the value of the field.
5501 * @err: print default error if failed.
5503 * Returns 0 on success -1 on field not found.
5505 int pevent_get_any_field_val(struct trace_seq
*s
, struct event_format
*event
,
5506 const char *name
, struct pevent_record
*record
,
5507 unsigned long long *val
, int err
)
5509 struct format_field
*field
;
5514 field
= pevent_find_any_field(event
, name
);
5516 return get_field_val(s
, field
, name
, record
, val
, err
);
5520 * pevent_print_num_field - print a field and a format
5521 * @s: The seq to print to
5522 * @fmt: The printf format to print the field with.
5523 * @event: the event that the field is for
5524 * @name: The name of the field
5525 * @record: The record with the field name.
5526 * @err: print default error if failed.
5528 * Returns: 0 on success, -1 field not found, or 1 if buffer is full.
5530 int pevent_print_num_field(struct trace_seq
*s
, const char *fmt
,
5531 struct event_format
*event
, const char *name
,
5532 struct pevent_record
*record
, int err
)
5534 struct format_field
*field
= pevent_find_field(event
, name
);
5535 unsigned long long val
;
5540 if (pevent_read_number_field(field
, record
->data
, &val
))
5543 return trace_seq_printf(s
, fmt
, val
);
5547 trace_seq_printf(s
, "CAN'T FIND FIELD \"%s\"", name
);
5552 * pevent_print_func_field - print a field and a format for function pointers
5553 * @s: The seq to print to
5554 * @fmt: The printf format to print the field with.
5555 * @event: the event that the field is for
5556 * @name: The name of the field
5557 * @record: The record with the field name.
5558 * @err: print default error if failed.
5560 * Returns: 0 on success, -1 field not found, or 1 if buffer is full.
5562 int pevent_print_func_field(struct trace_seq
*s
, const char *fmt
,
5563 struct event_format
*event
, const char *name
,
5564 struct pevent_record
*record
, int err
)
5566 struct format_field
*field
= pevent_find_field(event
, name
);
5567 struct pevent
*pevent
= event
->pevent
;
5568 unsigned long long val
;
5569 struct func_map
*func
;
5575 if (pevent_read_number_field(field
, record
->data
, &val
))
5578 func
= find_func(pevent
, val
);
5581 snprintf(tmp
, 128, "%s/0x%llx", func
->func
, func
->addr
- val
);
5583 sprintf(tmp
, "0x%08llx", val
);
5585 return trace_seq_printf(s
, fmt
, tmp
);
5589 trace_seq_printf(s
, "CAN'T FIND FIELD \"%s\"", name
);
5593 static void free_func_handle(struct pevent_function_handler
*func
)
5595 struct pevent_func_params
*params
;
5599 while (func
->params
) {
5600 params
= func
->params
;
5601 func
->params
= params
->next
;
5609 * pevent_register_print_function - register a helper function
5610 * @pevent: the handle to the pevent
5611 * @func: the function to process the helper function
5612 * @ret_type: the return type of the helper function
5613 * @name: the name of the helper function
5614 * @parameters: A list of enum pevent_func_arg_type
5616 * Some events may have helper functions in the print format arguments.
5617 * This allows a plugin to dynamically create a way to process one
5618 * of these functions.
5620 * The @parameters is a variable list of pevent_func_arg_type enums that
5621 * must end with PEVENT_FUNC_ARG_VOID.
5623 int pevent_register_print_function(struct pevent
*pevent
,
5624 pevent_func_handler func
,
5625 enum pevent_func_arg_type ret_type
,
5628 struct pevent_function_handler
*func_handle
;
5629 struct pevent_func_params
**next_param
;
5630 struct pevent_func_params
*param
;
5631 enum pevent_func_arg_type type
;
5635 func_handle
= find_func_handler(pevent
, name
);
5638 * This is most like caused by the users own
5639 * plugins updating the function. This overrides the
5642 pr_stat("override of function helper '%s'", name
);
5643 remove_func_handler(pevent
, name
);
5646 func_handle
= calloc(1, sizeof(*func_handle
));
5648 do_warning("Failed to allocate function handler");
5649 return PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5652 func_handle
->ret_type
= ret_type
;
5653 func_handle
->name
= strdup(name
);
5654 func_handle
->func
= func
;
5655 if (!func_handle
->name
) {
5656 do_warning("Failed to allocate function name");
5658 return PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5661 next_param
= &(func_handle
->params
);
5664 type
= va_arg(ap
, enum pevent_func_arg_type
);
5665 if (type
== PEVENT_FUNC_ARG_VOID
)
5668 if (type
>= PEVENT_FUNC_ARG_MAX_TYPES
) {
5669 do_warning("Invalid argument type %d", type
);
5670 ret
= PEVENT_ERRNO__INVALID_ARG_TYPE
;
5674 param
= malloc(sizeof(*param
));
5676 do_warning("Failed to allocate function param");
5677 ret
= PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5683 *next_param
= param
;
5684 next_param
= &(param
->next
);
5686 func_handle
->nr_args
++;
5690 func_handle
->next
= pevent
->func_handlers
;
5691 pevent
->func_handlers
= func_handle
;
5696 free_func_handle(func_handle
);
5701 * pevent_unregister_print_function - unregister a helper function
5702 * @pevent: the handle to the pevent
5703 * @func: the function to process the helper function
5704 * @name: the name of the helper function
5706 * This function removes existing print handler for function @name.
5708 * Returns 0 if the handler was removed successully, -1 otherwise.
5710 int pevent_unregister_print_function(struct pevent
*pevent
,
5711 pevent_func_handler func
, char *name
)
5713 struct pevent_function_handler
*func_handle
;
5715 func_handle
= find_func_handler(pevent
, name
);
5716 if (func_handle
&& func_handle
->func
== func
) {
5717 remove_func_handler(pevent
, name
);
5723 static struct event_format
*pevent_search_event(struct pevent
*pevent
, int id
,
5724 const char *sys_name
,
5725 const char *event_name
)
5727 struct event_format
*event
;
5731 event
= pevent_find_event(pevent
, id
);
5734 if (event_name
&& (strcmp(event_name
, event
->name
) != 0))
5736 if (sys_name
&& (strcmp(sys_name
, event
->system
) != 0))
5739 event
= pevent_find_event_by_name(pevent
, sys_name
, event_name
);
5747 * pevent_register_event_handler - register a way to parse an event
5748 * @pevent: the handle to the pevent
5749 * @id: the id of the event to register
5750 * @sys_name: the system name the event belongs to
5751 * @event_name: the name of the event
5752 * @func: the function to call to parse the event information
5753 * @context: the data to be passed to @func
5755 * This function allows a developer to override the parsing of
5756 * a given event. If for some reason the default print format
5757 * is not sufficient, this function will register a function
5758 * for an event to be used to parse the data instead.
5760 * If @id is >= 0, then it is used to find the event.
5761 * else @sys_name and @event_name are used.
5763 int pevent_register_event_handler(struct pevent
*pevent
, int id
,
5764 const char *sys_name
, const char *event_name
,
5765 pevent_event_handler_func func
, void *context
)
5767 struct event_format
*event
;
5768 struct event_handler
*handle
;
5770 event
= pevent_search_event(pevent
, id
, sys_name
, event_name
);
5774 pr_stat("overriding event (%d) %s:%s with new print handler",
5775 event
->id
, event
->system
, event
->name
);
5777 event
->handler
= func
;
5778 event
->context
= context
;
5782 /* Save for later use. */
5783 handle
= calloc(1, sizeof(*handle
));
5785 do_warning("Failed to allocate event handler");
5786 return PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5791 handle
->event_name
= strdup(event_name
);
5793 handle
->sys_name
= strdup(sys_name
);
5795 if ((event_name
&& !handle
->event_name
) ||
5796 (sys_name
&& !handle
->sys_name
)) {
5797 do_warning("Failed to allocate event/sys name");
5798 free((void *)handle
->event_name
);
5799 free((void *)handle
->sys_name
);
5801 return PEVENT_ERRNO__MEM_ALLOC_FAILED
;
5804 handle
->func
= func
;
5805 handle
->next
= pevent
->handlers
;
5806 pevent
->handlers
= handle
;
5807 handle
->context
= context
;
5812 static int handle_matches(struct event_handler
*handler
, int id
,
5813 const char *sys_name
, const char *event_name
,
5814 pevent_event_handler_func func
, void *context
)
5816 if (id
>= 0 && id
!= handler
->id
)
5819 if (event_name
&& (strcmp(event_name
, handler
->event_name
) != 0))
5822 if (sys_name
&& (strcmp(sys_name
, handler
->sys_name
) != 0))
5825 if (func
!= handler
->func
|| context
!= handler
->context
)
5832 * pevent_unregister_event_handler - unregister an existing event handler
5833 * @pevent: the handle to the pevent
5834 * @id: the id of the event to unregister
5835 * @sys_name: the system name the handler belongs to
5836 * @event_name: the name of the event handler
5837 * @func: the function to call to parse the event information
5838 * @context: the data to be passed to @func
5840 * This function removes existing event handler (parser).
5842 * If @id is >= 0, then it is used to find the event.
5843 * else @sys_name and @event_name are used.
5845 * Returns 0 if handler was removed successfully, -1 if event was not found.
5847 int pevent_unregister_event_handler(struct pevent
*pevent
, int id
,
5848 const char *sys_name
, const char *event_name
,
5849 pevent_event_handler_func func
, void *context
)
5851 struct event_format
*event
;
5852 struct event_handler
*handle
;
5853 struct event_handler
**next
;
5855 event
= pevent_search_event(pevent
, id
, sys_name
, event_name
);
5859 if (event
->handler
== func
&& event
->context
== context
) {
5860 pr_stat("removing override handler for event (%d) %s:%s. Going back to default handler.",
5861 event
->id
, event
->system
, event
->name
);
5863 event
->handler
= NULL
;
5864 event
->context
= NULL
;
5869 for (next
= &pevent
->handlers
; *next
; next
= &(*next
)->next
) {
5871 if (handle_matches(handle
, id
, sys_name
, event_name
,
5879 *next
= handle
->next
;
5880 free_handler(handle
);
5886 * pevent_alloc - create a pevent handle
5888 struct pevent
*pevent_alloc(void)
5890 struct pevent
*pevent
= calloc(1, sizeof(*pevent
));
5893 pevent
->ref_count
= 1;
5898 void pevent_ref(struct pevent
*pevent
)
5900 pevent
->ref_count
++;
5903 static void free_format_fields(struct format_field
*field
)
5905 struct format_field
*next
;
5916 static void free_formats(struct format
*format
)
5918 free_format_fields(format
->common_fields
);
5919 free_format_fields(format
->fields
);
5922 void pevent_free_format(struct event_format
*event
)
5925 free(event
->system
);
5927 free_formats(&event
->format
);
5929 free(event
->print_fmt
.format
);
5930 free_args(event
->print_fmt
.args
);
5936 * pevent_free - free a pevent handle
5937 * @pevent: the pevent handle to free
5939 void pevent_free(struct pevent
*pevent
)
5941 struct cmdline_list
*cmdlist
, *cmdnext
;
5942 struct func_list
*funclist
, *funcnext
;
5943 struct printk_list
*printklist
, *printknext
;
5944 struct pevent_function_handler
*func_handler
;
5945 struct event_handler
*handle
;
5951 cmdlist
= pevent
->cmdlist
;
5952 funclist
= pevent
->funclist
;
5953 printklist
= pevent
->printklist
;
5955 pevent
->ref_count
--;
5956 if (pevent
->ref_count
)
5959 if (pevent
->cmdlines
) {
5960 for (i
= 0; i
< pevent
->cmdline_count
; i
++)
5961 free(pevent
->cmdlines
[i
].comm
);
5962 free(pevent
->cmdlines
);
5966 cmdnext
= cmdlist
->next
;
5967 free(cmdlist
->comm
);
5972 if (pevent
->func_map
) {
5973 for (i
= 0; i
< (int)pevent
->func_count
; i
++) {
5974 free(pevent
->func_map
[i
].func
);
5975 free(pevent
->func_map
[i
].mod
);
5977 free(pevent
->func_map
);
5981 funcnext
= funclist
->next
;
5982 free(funclist
->func
);
5983 free(funclist
->mod
);
5985 funclist
= funcnext
;
5988 while (pevent
->func_handlers
) {
5989 func_handler
= pevent
->func_handlers
;
5990 pevent
->func_handlers
= func_handler
->next
;
5991 free_func_handle(func_handler
);
5994 if (pevent
->printk_map
) {
5995 for (i
= 0; i
< (int)pevent
->printk_count
; i
++)
5996 free(pevent
->printk_map
[i
].printk
);
5997 free(pevent
->printk_map
);
6000 while (printklist
) {
6001 printknext
= printklist
->next
;
6002 free(printklist
->printk
);
6004 printklist
= printknext
;
6007 for (i
= 0; i
< pevent
->nr_events
; i
++)
6008 pevent_free_format(pevent
->events
[i
]);
6010 while (pevent
->handlers
) {
6011 handle
= pevent
->handlers
;
6012 pevent
->handlers
= handle
->next
;
6013 free_handler(handle
);
6016 free(pevent
->events
);
6017 free(pevent
->sort_events
);
6022 void pevent_unref(struct pevent
*pevent
)
6024 pevent_free(pevent
);