diff options
| author | Steven Rostedt <srostedt@redhat.com> | 2009-11-23 21:46:35 -0500 |
|---|---|---|
| committer | Steven Rostedt <rostedt@goodmis.org> | 2009-11-23 21:46:35 -0500 |
| commit | 4a8ad9041eaaf8019b0488dc598efe38d07a5220 (patch) | |
| tree | ade3cacadc1c85778d230955fe55762643f2ed5a | |
| parent | 28c86bb67da8dc23c109f13cbf2ade4dbbda5ac8 (diff) | |
Add handling of __get_dynamic_array
This adds some code to handle direct uses of __dynamic_array.
It still needs to handle the type casting for it.
Signed-off-by: Steven Rostedt <rostedt@goodmis.org>
| -rw-r--r-- | parse-events.c | 103 | ||||
| -rw-r--r-- | parse-events.h | 7 |
2 files changed, 100 insertions, 10 deletions
diff --git a/parse-events.c b/parse-events.c index 6478efc..e7e2fc0 100644 --- a/parse-events.c +++ b/parse-events.c | |||
| @@ -49,6 +49,8 @@ static unsigned long long input_buf_siz; | |||
| 49 | static int cpus; | 49 | static int cpus; |
| 50 | static int long_size; | 50 | static int long_size; |
| 51 | 51 | ||
| 52 | static struct format_field *find_field(struct event *event, const char *name); | ||
| 53 | |||
| 52 | static void init_input_buf(char *buf, unsigned long long size) | 54 | static void init_input_buf(char *buf, unsigned long long size) |
| 53 | { | 55 | { |
| 54 | input_buf = buf; | 56 | input_buf = buf; |
| @@ -1593,6 +1595,63 @@ out_free: | |||
| 1593 | } | 1595 | } |
| 1594 | 1596 | ||
| 1595 | static enum event_type | 1597 | static enum event_type |
| 1598 | process_dynamic_array(struct event *event, struct print_arg *arg, char **tok) | ||
| 1599 | { | ||
| 1600 | struct format_field *field; | ||
| 1601 | enum event_type type; | ||
| 1602 | char *token; | ||
| 1603 | |||
| 1604 | memset(arg, 0, sizeof(*arg)); | ||
| 1605 | arg->type = PRINT_DYNAMIC_ARRAY; | ||
| 1606 | |||
| 1607 | if (read_expected_item(EVENT_DELIM, "(") < 0) | ||
| 1608 | return EVENT_ERROR; | ||
| 1609 | |||
| 1610 | /* | ||
| 1611 | * The item within the parenthesis is another field that holds | ||
| 1612 | * the index into where the array starts. | ||
| 1613 | */ | ||
| 1614 | type = read_token(&token); | ||
| 1615 | *tok = token; | ||
| 1616 | if (type != EVENT_ITEM) | ||
| 1617 | return EVENT_ERROR; | ||
| 1618 | |||
| 1619 | /* Find the field */ | ||
| 1620 | |||
| 1621 | field = find_field(event, token); | ||
| 1622 | if (!field) | ||
| 1623 | return EVENT_ERROR; | ||
| 1624 | |||
| 1625 | arg->dynarray.field = field; | ||
| 1626 | arg->dynarray.index = 0; | ||
| 1627 | |||
| 1628 | if (read_expected(EVENT_DELIM, ")") < 0) | ||
| 1629 | return EVENT_ERROR; | ||
| 1630 | |||
| 1631 | type = read_token_item(&token); | ||
| 1632 | *tok = token; | ||
| 1633 | if (type != EVENT_OP || strcmp(token, "[") != 0) | ||
| 1634 | return type; | ||
| 1635 | |||
| 1636 | free_token(token); | ||
| 1637 | arg = malloc_or_die(sizeof(*arg)); | ||
| 1638 | type = process_arg(event, arg, &token); | ||
| 1639 | if (type == EVENT_ERROR) | ||
| 1640 | goto out_free; | ||
| 1641 | |||
| 1642 | if (!test_type_token(type, token, EVENT_OP, "]")) | ||
| 1643 | goto out_free; | ||
| 1644 | |||
| 1645 | free_token(token); | ||
| 1646 | type = read_token_item(tok); | ||
| 1647 | return type; | ||
| 1648 | |||
| 1649 | out_free: | ||
| 1650 | free(arg); | ||
| 1651 | return EVENT_ERROR; | ||
| 1652 | } | ||
| 1653 | |||
| 1654 | static enum event_type | ||
| 1596 | process_paren(struct event *event, struct print_arg *arg, char **tok) | 1655 | process_paren(struct event *event, struct print_arg *arg, char **tok) |
| 1597 | { | 1656 | { |
| 1598 | struct print_arg *item_arg; | 1657 | struct print_arg *item_arg; |
| @@ -1696,6 +1755,9 @@ process_arg_token(struct event *event, struct print_arg *arg, | |||
| 1696 | } else if (strcmp(token, "__get_str") == 0) { | 1755 | } else if (strcmp(token, "__get_str") == 0) { |
| 1697 | free_token(token); | 1756 | free_token(token); |
| 1698 | type = process_str(event, arg, &token); | 1757 | type = process_str(event, arg, &token); |
| 1758 | } else if (strcmp(token, "__get_dynamic_array") == 0) { | ||
| 1759 | free_token(token); | ||
| 1760 | type = process_dynamic_array(event, arg, &token); | ||
| 1699 | } else { | 1761 | } else { |
| 1700 | atom = token; | 1762 | atom = token; |
| 1701 | /* test the next token */ | 1763 | /* test the next token */ |
| @@ -2014,6 +2076,8 @@ static unsigned long long eval_num_arg(void *data, int size, | |||
| 2014 | unsigned long long val = 0; | 2076 | unsigned long long val = 0; |
| 2015 | unsigned long long left, right; | 2077 | unsigned long long left, right; |
| 2016 | struct print_arg *larg; | 2078 | struct print_arg *larg; |
| 2079 | unsigned long offset; | ||
| 2080 | int len; | ||
| 2017 | 2081 | ||
| 2018 | switch (arg->type) { | 2082 | switch (arg->type) { |
| 2019 | case PRINT_NULL: | 2083 | case PRINT_NULL: |
| @@ -2045,18 +2109,37 @@ static unsigned long long eval_num_arg(void *data, int size, | |||
| 2045 | * Arrays are special, since we don't want | 2109 | * Arrays are special, since we don't want |
| 2046 | * to read the arg as is. | 2110 | * to read the arg as is. |
| 2047 | */ | 2111 | */ |
| 2048 | if (arg->op.left->type != PRINT_FIELD) | 2112 | right = eval_num_arg(data, size, event, arg->op.right); |
| 2113 | switch (arg->op.left->type) { | ||
| 2114 | case PRINT_DYNAMIC_ARRAY: | ||
| 2115 | breakpoint(); | ||
| 2116 | larg = arg->op.left; | ||
| 2117 | offset = read_size(data + larg->dynarray.field->offset, | ||
| 2118 | larg->dynarray.field->size); | ||
| 2119 | /* | ||
| 2120 | * The actual length of the dynamic array is stored | ||
| 2121 | * in the top half of the field, and the offset | ||
| 2122 | * is in the bottom half of the 32 bit field. | ||
| 2123 | */ | ||
| 2124 | offset &= 0xffff; | ||
| 2125 | offset += right; | ||
| 2126 | len = 1; | ||
| 2127 | break; | ||
| 2128 | case PRINT_FIELD: | ||
| 2129 | larg = arg->op.left; | ||
| 2130 | if (!larg->field.field) { | ||
| 2131 | larg->field.field = | ||
| 2132 | find_any_field(event, larg->field.name); | ||
| 2133 | if (!larg->field.field) | ||
| 2134 | die("field %s not found", larg->field.name); | ||
| 2135 | } | ||
| 2136 | offset = larg->field.field->offset + | ||
| 2137 | right * long_size; | ||
| 2138 | len = long_size; | ||
| 2139 | default: | ||
| 2049 | goto default_op; /* oops, all bets off */ | 2140 | goto default_op; /* oops, all bets off */ |
| 2050 | larg = arg->op.left; | ||
| 2051 | if (!larg->field.field) { | ||
| 2052 | larg->field.field = | ||
| 2053 | find_any_field(event, larg->field.name); | ||
| 2054 | if (!larg->field.field) | ||
| 2055 | die("field %s not found", larg->field.name); | ||
| 2056 | } | 2141 | } |
| 2057 | right = eval_num_arg(data, size, event, arg->op.right); | 2142 | val = read_size(data + offset, len); |
| 2058 | val = read_size(data + larg->field.field->offset + | ||
| 2059 | right * long_size, long_size); | ||
| 2060 | break; | 2143 | break; |
| 2061 | } | 2144 | } |
| 2062 | default_op: | 2145 | default_op: |
diff --git a/parse-events.h b/parse-events.h index 4858a52..beee837 100644 --- a/parse-events.h +++ b/parse-events.h | |||
| @@ -88,6 +88,11 @@ struct print_arg_symbol { | |||
| 88 | struct print_flag_sym *symbols; | 88 | struct print_flag_sym *symbols; |
| 89 | }; | 89 | }; |
| 90 | 90 | ||
| 91 | struct print_arg_dynarray { | ||
| 92 | struct format_field *field; | ||
| 93 | struct print_arg *index; | ||
| 94 | }; | ||
| 95 | |||
| 91 | struct print_arg; | 96 | struct print_arg; |
| 92 | 97 | ||
| 93 | struct print_arg_op { | 98 | struct print_arg_op { |
| @@ -110,6 +115,7 @@ enum print_arg_type { | |||
| 110 | PRINT_SYMBOL, | 115 | PRINT_SYMBOL, |
| 111 | PRINT_TYPE, | 116 | PRINT_TYPE, |
| 112 | PRINT_STRING, | 117 | PRINT_STRING, |
| 118 | PRINT_DYNAMIC_ARRAY, | ||
| 113 | PRINT_OP, | 119 | PRINT_OP, |
| 114 | }; | 120 | }; |
| 115 | 121 | ||
| @@ -125,6 +131,7 @@ struct print_arg { | |||
| 125 | struct print_arg_func func; | 131 | struct print_arg_func func; |
| 126 | struct print_arg_string string; | 132 | struct print_arg_string string; |
| 127 | struct print_arg_op op; | 133 | struct print_arg_op op; |
| 134 | struct print_arg_dynarray dynarray; | ||
| 128 | }; | 135 | }; |
| 129 | }; | 136 | }; |
| 130 | 137 | ||
