xref: /OK3568_Linux_fs/kernel/tools/perf/util/parse-events.y (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun %define api.pure full
2*4882a593Smuzhiyun %parse-param {void *_parse_state}
3*4882a593Smuzhiyun %parse-param {void *scanner}
4*4882a593Smuzhiyun %lex-param {void* scanner}
5*4882a593Smuzhiyun %locations
6*4882a593Smuzhiyun 
7*4882a593Smuzhiyun %{
8*4882a593Smuzhiyun 
9*4882a593Smuzhiyun #define YYDEBUG 1
10*4882a593Smuzhiyun 
11*4882a593Smuzhiyun #include <fnmatch.h>
12*4882a593Smuzhiyun #include <stdio.h>
13*4882a593Smuzhiyun #include <linux/compiler.h>
14*4882a593Smuzhiyun #include <linux/types.h>
15*4882a593Smuzhiyun #include <linux/zalloc.h>
16*4882a593Smuzhiyun #include "pmu.h"
17*4882a593Smuzhiyun #include "evsel.h"
18*4882a593Smuzhiyun #include "parse-events.h"
19*4882a593Smuzhiyun #include "parse-events-bison.h"
20*4882a593Smuzhiyun 
21*4882a593Smuzhiyun void parse_events_error(YYLTYPE *loc, void *parse_state, void *scanner, char const *msg);
22*4882a593Smuzhiyun 
23*4882a593Smuzhiyun #define ABORT_ON(val) \
24*4882a593Smuzhiyun do { \
25*4882a593Smuzhiyun 	if (val) \
26*4882a593Smuzhiyun 		YYABORT; \
27*4882a593Smuzhiyun } while (0)
28*4882a593Smuzhiyun 
alloc_list(void)29*4882a593Smuzhiyun static struct list_head* alloc_list(void)
30*4882a593Smuzhiyun {
31*4882a593Smuzhiyun 	struct list_head *list;
32*4882a593Smuzhiyun 
33*4882a593Smuzhiyun 	list = malloc(sizeof(*list));
34*4882a593Smuzhiyun 	if (!list)
35*4882a593Smuzhiyun 		return NULL;
36*4882a593Smuzhiyun 
37*4882a593Smuzhiyun 	INIT_LIST_HEAD(list);
38*4882a593Smuzhiyun 	return list;
39*4882a593Smuzhiyun }
40*4882a593Smuzhiyun 
free_list_evsel(struct list_head * list_evsel)41*4882a593Smuzhiyun static void free_list_evsel(struct list_head* list_evsel)
42*4882a593Smuzhiyun {
43*4882a593Smuzhiyun 	struct evsel *evsel, *tmp;
44*4882a593Smuzhiyun 
45*4882a593Smuzhiyun 	list_for_each_entry_safe(evsel, tmp, list_evsel, core.node) {
46*4882a593Smuzhiyun 		list_del_init(&evsel->core.node);
47*4882a593Smuzhiyun 		evsel__delete(evsel);
48*4882a593Smuzhiyun 	}
49*4882a593Smuzhiyun 	free(list_evsel);
50*4882a593Smuzhiyun }
51*4882a593Smuzhiyun 
inc_group_count(struct list_head * list,struct parse_events_state * parse_state)52*4882a593Smuzhiyun static void inc_group_count(struct list_head *list,
53*4882a593Smuzhiyun 		       struct parse_events_state *parse_state)
54*4882a593Smuzhiyun {
55*4882a593Smuzhiyun 	/* Count groups only have more than 1 members */
56*4882a593Smuzhiyun 	if (!list_is_last(list->next, list))
57*4882a593Smuzhiyun 		parse_state->nr_groups++;
58*4882a593Smuzhiyun }
59*4882a593Smuzhiyun 
60*4882a593Smuzhiyun %}
61*4882a593Smuzhiyun 
62*4882a593Smuzhiyun %token PE_START_EVENTS PE_START_TERMS
63*4882a593Smuzhiyun %token PE_VALUE PE_VALUE_SYM_HW PE_VALUE_SYM_SW PE_RAW PE_TERM
64*4882a593Smuzhiyun %token PE_VALUE_SYM_TOOL
65*4882a593Smuzhiyun %token PE_EVENT_NAME
66*4882a593Smuzhiyun %token PE_NAME
67*4882a593Smuzhiyun %token PE_BPF_OBJECT PE_BPF_SOURCE
68*4882a593Smuzhiyun %token PE_MODIFIER_EVENT PE_MODIFIER_BP
69*4882a593Smuzhiyun %token PE_NAME_CACHE_TYPE PE_NAME_CACHE_OP_RESULT
70*4882a593Smuzhiyun %token PE_PREFIX_MEM PE_PREFIX_RAW PE_PREFIX_GROUP
71*4882a593Smuzhiyun %token PE_ERROR
72*4882a593Smuzhiyun %token PE_PMU_EVENT_PRE PE_PMU_EVENT_SUF PE_KERNEL_PMU_EVENT PE_PMU_EVENT_FAKE
73*4882a593Smuzhiyun %token PE_ARRAY_ALL PE_ARRAY_RANGE
74*4882a593Smuzhiyun %token PE_DRV_CFG_TERM
75*4882a593Smuzhiyun %type <num> PE_VALUE
76*4882a593Smuzhiyun %type <num> PE_VALUE_SYM_HW
77*4882a593Smuzhiyun %type <num> PE_VALUE_SYM_SW
78*4882a593Smuzhiyun %type <num> PE_VALUE_SYM_TOOL
79*4882a593Smuzhiyun %type <num> PE_RAW
80*4882a593Smuzhiyun %type <num> PE_TERM
81*4882a593Smuzhiyun %type <num> value_sym
82*4882a593Smuzhiyun %type <str> PE_NAME
83*4882a593Smuzhiyun %type <str> PE_BPF_OBJECT
84*4882a593Smuzhiyun %type <str> PE_BPF_SOURCE
85*4882a593Smuzhiyun %type <str> PE_NAME_CACHE_TYPE
86*4882a593Smuzhiyun %type <str> PE_NAME_CACHE_OP_RESULT
87*4882a593Smuzhiyun %type <str> PE_MODIFIER_EVENT
88*4882a593Smuzhiyun %type <str> PE_MODIFIER_BP
89*4882a593Smuzhiyun %type <str> PE_EVENT_NAME
90*4882a593Smuzhiyun %type <str> PE_PMU_EVENT_PRE PE_PMU_EVENT_SUF PE_KERNEL_PMU_EVENT PE_PMU_EVENT_FAKE
91*4882a593Smuzhiyun %type <str> PE_DRV_CFG_TERM
92*4882a593Smuzhiyun %destructor { free ($$); } <str>
93*4882a593Smuzhiyun %type <term> event_term
94*4882a593Smuzhiyun %destructor { parse_events_term__delete ($$); } <term>
95*4882a593Smuzhiyun %type <list_terms> event_config
96*4882a593Smuzhiyun %type <list_terms> opt_event_config
97*4882a593Smuzhiyun %type <list_terms> opt_pmu_config
98*4882a593Smuzhiyun %destructor { parse_events_terms__delete ($$); } <list_terms>
99*4882a593Smuzhiyun %type <list_evsel> event_pmu
100*4882a593Smuzhiyun %type <list_evsel> event_legacy_symbol
101*4882a593Smuzhiyun %type <list_evsel> event_legacy_cache
102*4882a593Smuzhiyun %type <list_evsel> event_legacy_mem
103*4882a593Smuzhiyun %type <list_evsel> event_legacy_tracepoint
104*4882a593Smuzhiyun %type <list_evsel> event_legacy_numeric
105*4882a593Smuzhiyun %type <list_evsel> event_legacy_raw
106*4882a593Smuzhiyun %type <list_evsel> event_bpf_file
107*4882a593Smuzhiyun %type <list_evsel> event_def
108*4882a593Smuzhiyun %type <list_evsel> event_mod
109*4882a593Smuzhiyun %type <list_evsel> event_name
110*4882a593Smuzhiyun %type <list_evsel> event
111*4882a593Smuzhiyun %type <list_evsel> events
112*4882a593Smuzhiyun %type <list_evsel> group_def
113*4882a593Smuzhiyun %type <list_evsel> group
114*4882a593Smuzhiyun %type <list_evsel> groups
115*4882a593Smuzhiyun %destructor { free_list_evsel ($$); } <list_evsel>
116*4882a593Smuzhiyun %type <tracepoint_name> tracepoint_name
117*4882a593Smuzhiyun %destructor { free ($$.sys); free ($$.event); } <tracepoint_name>
118*4882a593Smuzhiyun %type <array> array
119*4882a593Smuzhiyun %type <array> array_term
120*4882a593Smuzhiyun %type <array> array_terms
121*4882a593Smuzhiyun %destructor { free ($$.ranges); } <array>
122*4882a593Smuzhiyun 
123*4882a593Smuzhiyun %union
124*4882a593Smuzhiyun {
125*4882a593Smuzhiyun 	char *str;
126*4882a593Smuzhiyun 	u64 num;
127*4882a593Smuzhiyun 	struct list_head *list_evsel;
128*4882a593Smuzhiyun 	struct list_head *list_terms;
129*4882a593Smuzhiyun 	struct parse_events_term *term;
130*4882a593Smuzhiyun 	struct tracepoint_name {
131*4882a593Smuzhiyun 		char *sys;
132*4882a593Smuzhiyun 		char *event;
133*4882a593Smuzhiyun 	} tracepoint_name;
134*4882a593Smuzhiyun 	struct parse_events_array array;
135*4882a593Smuzhiyun }
136*4882a593Smuzhiyun %%
137*4882a593Smuzhiyun 
138*4882a593Smuzhiyun start:
139*4882a593Smuzhiyun PE_START_EVENTS start_events
140*4882a593Smuzhiyun |
141*4882a593Smuzhiyun PE_START_TERMS  start_terms
142*4882a593Smuzhiyun 
143*4882a593Smuzhiyun start_events: groups
144*4882a593Smuzhiyun {
145*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
146*4882a593Smuzhiyun 
147*4882a593Smuzhiyun 	/* frees $1 */
148*4882a593Smuzhiyun 	parse_events_update_lists($1, &parse_state->list);
149*4882a593Smuzhiyun }
150*4882a593Smuzhiyun 
151*4882a593Smuzhiyun groups:
152*4882a593Smuzhiyun groups ',' group
153*4882a593Smuzhiyun {
154*4882a593Smuzhiyun 	struct list_head *list  = $1;
155*4882a593Smuzhiyun 	struct list_head *group = $3;
156*4882a593Smuzhiyun 
157*4882a593Smuzhiyun 	/* frees $3 */
158*4882a593Smuzhiyun 	parse_events_update_lists(group, list);
159*4882a593Smuzhiyun 	$$ = list;
160*4882a593Smuzhiyun }
161*4882a593Smuzhiyun |
162*4882a593Smuzhiyun groups ',' event
163*4882a593Smuzhiyun {
164*4882a593Smuzhiyun 	struct list_head *list  = $1;
165*4882a593Smuzhiyun 	struct list_head *event = $3;
166*4882a593Smuzhiyun 
167*4882a593Smuzhiyun 	/* frees $3 */
168*4882a593Smuzhiyun 	parse_events_update_lists(event, list);
169*4882a593Smuzhiyun 	$$ = list;
170*4882a593Smuzhiyun }
171*4882a593Smuzhiyun |
172*4882a593Smuzhiyun group
173*4882a593Smuzhiyun |
174*4882a593Smuzhiyun event
175*4882a593Smuzhiyun 
176*4882a593Smuzhiyun group:
177*4882a593Smuzhiyun group_def ':' PE_MODIFIER_EVENT
178*4882a593Smuzhiyun {
179*4882a593Smuzhiyun 	struct list_head *list = $1;
180*4882a593Smuzhiyun 	int err;
181*4882a593Smuzhiyun 
182*4882a593Smuzhiyun 	err = parse_events__modifier_group(list, $3);
183*4882a593Smuzhiyun 	free($3);
184*4882a593Smuzhiyun 	if (err) {
185*4882a593Smuzhiyun 		free_list_evsel(list);
186*4882a593Smuzhiyun 		YYABORT;
187*4882a593Smuzhiyun 	}
188*4882a593Smuzhiyun 	$$ = list;
189*4882a593Smuzhiyun }
190*4882a593Smuzhiyun |
191*4882a593Smuzhiyun group_def
192*4882a593Smuzhiyun 
193*4882a593Smuzhiyun group_def:
194*4882a593Smuzhiyun PE_NAME '{' events '}'
195*4882a593Smuzhiyun {
196*4882a593Smuzhiyun 	struct list_head *list = $3;
197*4882a593Smuzhiyun 
198*4882a593Smuzhiyun 	inc_group_count(list, _parse_state);
199*4882a593Smuzhiyun 	parse_events__set_leader($1, list, _parse_state);
200*4882a593Smuzhiyun 	free($1);
201*4882a593Smuzhiyun 	$$ = list;
202*4882a593Smuzhiyun }
203*4882a593Smuzhiyun |
204*4882a593Smuzhiyun '{' events '}'
205*4882a593Smuzhiyun {
206*4882a593Smuzhiyun 	struct list_head *list = $2;
207*4882a593Smuzhiyun 
208*4882a593Smuzhiyun 	inc_group_count(list, _parse_state);
209*4882a593Smuzhiyun 	parse_events__set_leader(NULL, list, _parse_state);
210*4882a593Smuzhiyun 	$$ = list;
211*4882a593Smuzhiyun }
212*4882a593Smuzhiyun 
213*4882a593Smuzhiyun events:
214*4882a593Smuzhiyun events ',' event
215*4882a593Smuzhiyun {
216*4882a593Smuzhiyun 	struct list_head *event = $3;
217*4882a593Smuzhiyun 	struct list_head *list  = $1;
218*4882a593Smuzhiyun 
219*4882a593Smuzhiyun 	/* frees $3 */
220*4882a593Smuzhiyun 	parse_events_update_lists(event, list);
221*4882a593Smuzhiyun 	$$ = list;
222*4882a593Smuzhiyun }
223*4882a593Smuzhiyun |
224*4882a593Smuzhiyun event
225*4882a593Smuzhiyun 
226*4882a593Smuzhiyun event: event_mod
227*4882a593Smuzhiyun 
228*4882a593Smuzhiyun event_mod:
229*4882a593Smuzhiyun event_name PE_MODIFIER_EVENT
230*4882a593Smuzhiyun {
231*4882a593Smuzhiyun 	struct list_head *list = $1;
232*4882a593Smuzhiyun 	int err;
233*4882a593Smuzhiyun 
234*4882a593Smuzhiyun 	/*
235*4882a593Smuzhiyun 	 * Apply modifier on all events added by single event definition
236*4882a593Smuzhiyun 	 * (there could be more events added for multiple tracepoint
237*4882a593Smuzhiyun 	 * definitions via '*?'.
238*4882a593Smuzhiyun 	 */
239*4882a593Smuzhiyun 	err = parse_events__modifier_event(list, $2, false);
240*4882a593Smuzhiyun 	free($2);
241*4882a593Smuzhiyun 	if (err) {
242*4882a593Smuzhiyun 		free_list_evsel(list);
243*4882a593Smuzhiyun 		YYABORT;
244*4882a593Smuzhiyun 	}
245*4882a593Smuzhiyun 	$$ = list;
246*4882a593Smuzhiyun }
247*4882a593Smuzhiyun |
248*4882a593Smuzhiyun event_name
249*4882a593Smuzhiyun 
250*4882a593Smuzhiyun event_name:
251*4882a593Smuzhiyun PE_EVENT_NAME event_def
252*4882a593Smuzhiyun {
253*4882a593Smuzhiyun 	int err;
254*4882a593Smuzhiyun 
255*4882a593Smuzhiyun 	err = parse_events_name($2, $1);
256*4882a593Smuzhiyun 	free($1);
257*4882a593Smuzhiyun 	if (err) {
258*4882a593Smuzhiyun 		free_list_evsel($2);
259*4882a593Smuzhiyun 		YYABORT;
260*4882a593Smuzhiyun 	}
261*4882a593Smuzhiyun 	$$ = $2;
262*4882a593Smuzhiyun }
263*4882a593Smuzhiyun |
264*4882a593Smuzhiyun event_def
265*4882a593Smuzhiyun 
266*4882a593Smuzhiyun event_def: event_pmu |
267*4882a593Smuzhiyun 	   event_legacy_symbol |
268*4882a593Smuzhiyun 	   event_legacy_cache sep_dc |
269*4882a593Smuzhiyun 	   event_legacy_mem |
270*4882a593Smuzhiyun 	   event_legacy_tracepoint sep_dc |
271*4882a593Smuzhiyun 	   event_legacy_numeric sep_dc |
272*4882a593Smuzhiyun 	   event_legacy_raw sep_dc |
273*4882a593Smuzhiyun 	   event_bpf_file
274*4882a593Smuzhiyun 
275*4882a593Smuzhiyun event_pmu:
276*4882a593Smuzhiyun PE_NAME opt_pmu_config
277*4882a593Smuzhiyun {
278*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
279*4882a593Smuzhiyun 	struct parse_events_error *error = parse_state->error;
280*4882a593Smuzhiyun 	struct list_head *list = NULL, *orig_terms = NULL, *terms= NULL;
281*4882a593Smuzhiyun 	char *pattern = NULL;
282*4882a593Smuzhiyun 
283*4882a593Smuzhiyun #define CLEANUP_YYABORT					\
284*4882a593Smuzhiyun 	do {						\
285*4882a593Smuzhiyun 		parse_events_terms__delete($2);		\
286*4882a593Smuzhiyun 		parse_events_terms__delete(orig_terms);	\
287*4882a593Smuzhiyun 		free(list);				\
288*4882a593Smuzhiyun 		free($1);				\
289*4882a593Smuzhiyun 		free(pattern);				\
290*4882a593Smuzhiyun 		YYABORT;				\
291*4882a593Smuzhiyun 	} while(0)
292*4882a593Smuzhiyun 
293*4882a593Smuzhiyun 	if (parse_events_copy_term_list($2, &orig_terms))
294*4882a593Smuzhiyun 		CLEANUP_YYABORT;
295*4882a593Smuzhiyun 
296*4882a593Smuzhiyun 	if (error)
297*4882a593Smuzhiyun 		error->idx = @1.first_column;
298*4882a593Smuzhiyun 
299*4882a593Smuzhiyun 	list = alloc_list();
300*4882a593Smuzhiyun 	if (!list)
301*4882a593Smuzhiyun 		CLEANUP_YYABORT;
302*4882a593Smuzhiyun 	if (parse_events_add_pmu(_parse_state, list, $1, $2, false, false)) {
303*4882a593Smuzhiyun 		struct perf_pmu *pmu = NULL;
304*4882a593Smuzhiyun 		int ok = 0;
305*4882a593Smuzhiyun 
306*4882a593Smuzhiyun 		if (asprintf(&pattern, "%s*", $1) < 0)
307*4882a593Smuzhiyun 			CLEANUP_YYABORT;
308*4882a593Smuzhiyun 
309*4882a593Smuzhiyun 		while ((pmu = perf_pmu__scan(pmu)) != NULL) {
310*4882a593Smuzhiyun 			char *name = pmu->name;
311*4882a593Smuzhiyun 
312*4882a593Smuzhiyun 			if (!strncmp(name, "uncore_", 7) &&
313*4882a593Smuzhiyun 			    strncmp($1, "uncore_", 7))
314*4882a593Smuzhiyun 				name += 7;
315*4882a593Smuzhiyun 			if (!fnmatch(pattern, name, 0)) {
316*4882a593Smuzhiyun 				if (parse_events_copy_term_list(orig_terms, &terms))
317*4882a593Smuzhiyun 					CLEANUP_YYABORT;
318*4882a593Smuzhiyun 				if (!parse_events_add_pmu(_parse_state, list, pmu->name, terms, true, false))
319*4882a593Smuzhiyun 					ok++;
320*4882a593Smuzhiyun 				parse_events_terms__delete(terms);
321*4882a593Smuzhiyun 			}
322*4882a593Smuzhiyun 		}
323*4882a593Smuzhiyun 
324*4882a593Smuzhiyun 		if (!ok)
325*4882a593Smuzhiyun 			CLEANUP_YYABORT;
326*4882a593Smuzhiyun 	}
327*4882a593Smuzhiyun 	parse_events_terms__delete($2);
328*4882a593Smuzhiyun 	parse_events_terms__delete(orig_terms);
329*4882a593Smuzhiyun 	free(pattern);
330*4882a593Smuzhiyun 	free($1);
331*4882a593Smuzhiyun 	$$ = list;
332*4882a593Smuzhiyun #undef CLEANUP_YYABORT
333*4882a593Smuzhiyun }
334*4882a593Smuzhiyun |
335*4882a593Smuzhiyun PE_KERNEL_PMU_EVENT sep_dc
336*4882a593Smuzhiyun {
337*4882a593Smuzhiyun 	struct list_head *list;
338*4882a593Smuzhiyun 	int err;
339*4882a593Smuzhiyun 
340*4882a593Smuzhiyun 	err = parse_events_multi_pmu_add(_parse_state, $1, &list);
341*4882a593Smuzhiyun 	free($1);
342*4882a593Smuzhiyun 	if (err < 0)
343*4882a593Smuzhiyun 		YYABORT;
344*4882a593Smuzhiyun 	$$ = list;
345*4882a593Smuzhiyun }
346*4882a593Smuzhiyun |
347*4882a593Smuzhiyun PE_PMU_EVENT_PRE '-' PE_PMU_EVENT_SUF sep_dc
348*4882a593Smuzhiyun {
349*4882a593Smuzhiyun 	struct list_head *list;
350*4882a593Smuzhiyun 	char pmu_name[128];
351*4882a593Smuzhiyun 
352*4882a593Smuzhiyun 	snprintf(pmu_name, sizeof(pmu_name), "%s-%s", $1, $3);
353*4882a593Smuzhiyun 	free($1);
354*4882a593Smuzhiyun 	free($3);
355*4882a593Smuzhiyun 	if (parse_events_multi_pmu_add(_parse_state, pmu_name, &list) < 0)
356*4882a593Smuzhiyun 		YYABORT;
357*4882a593Smuzhiyun 	$$ = list;
358*4882a593Smuzhiyun }
359*4882a593Smuzhiyun |
360*4882a593Smuzhiyun PE_PMU_EVENT_FAKE sep_dc
361*4882a593Smuzhiyun {
362*4882a593Smuzhiyun 	struct list_head *list;
363*4882a593Smuzhiyun 	int err;
364*4882a593Smuzhiyun 
365*4882a593Smuzhiyun 	list = alloc_list();
366*4882a593Smuzhiyun 	if (!list)
367*4882a593Smuzhiyun 		YYABORT;
368*4882a593Smuzhiyun 
369*4882a593Smuzhiyun 	err = parse_events_add_pmu(_parse_state, list, $1, NULL, false, false);
370*4882a593Smuzhiyun 	free($1);
371*4882a593Smuzhiyun 	if (err < 0) {
372*4882a593Smuzhiyun 		free(list);
373*4882a593Smuzhiyun 		YYABORT;
374*4882a593Smuzhiyun 	}
375*4882a593Smuzhiyun 	$$ = list;
376*4882a593Smuzhiyun }
377*4882a593Smuzhiyun |
378*4882a593Smuzhiyun PE_PMU_EVENT_FAKE opt_pmu_config
379*4882a593Smuzhiyun {
380*4882a593Smuzhiyun 	struct list_head *list;
381*4882a593Smuzhiyun 	int err;
382*4882a593Smuzhiyun 
383*4882a593Smuzhiyun 	list = alloc_list();
384*4882a593Smuzhiyun 	if (!list)
385*4882a593Smuzhiyun 		YYABORT;
386*4882a593Smuzhiyun 
387*4882a593Smuzhiyun 	err = parse_events_add_pmu(_parse_state, list, $1, $2, false, false);
388*4882a593Smuzhiyun 	free($1);
389*4882a593Smuzhiyun 	parse_events_terms__delete($2);
390*4882a593Smuzhiyun 	if (err < 0) {
391*4882a593Smuzhiyun 		free(list);
392*4882a593Smuzhiyun 		YYABORT;
393*4882a593Smuzhiyun 	}
394*4882a593Smuzhiyun 	$$ = list;
395*4882a593Smuzhiyun }
396*4882a593Smuzhiyun 
397*4882a593Smuzhiyun value_sym:
398*4882a593Smuzhiyun PE_VALUE_SYM_HW
399*4882a593Smuzhiyun |
400*4882a593Smuzhiyun PE_VALUE_SYM_SW
401*4882a593Smuzhiyun 
402*4882a593Smuzhiyun event_legacy_symbol:
403*4882a593Smuzhiyun value_sym '/' event_config '/'
404*4882a593Smuzhiyun {
405*4882a593Smuzhiyun 	struct list_head *list;
406*4882a593Smuzhiyun 	int type = $1 >> 16;
407*4882a593Smuzhiyun 	int config = $1 & 255;
408*4882a593Smuzhiyun 	int err;
409*4882a593Smuzhiyun 
410*4882a593Smuzhiyun 	list = alloc_list();
411*4882a593Smuzhiyun 	ABORT_ON(!list);
412*4882a593Smuzhiyun 	err = parse_events_add_numeric(_parse_state, list, type, config, $3);
413*4882a593Smuzhiyun 	parse_events_terms__delete($3);
414*4882a593Smuzhiyun 	if (err) {
415*4882a593Smuzhiyun 		free_list_evsel(list);
416*4882a593Smuzhiyun 		YYABORT;
417*4882a593Smuzhiyun 	}
418*4882a593Smuzhiyun 	$$ = list;
419*4882a593Smuzhiyun }
420*4882a593Smuzhiyun |
421*4882a593Smuzhiyun value_sym sep_slash_slash_dc
422*4882a593Smuzhiyun {
423*4882a593Smuzhiyun 	struct list_head *list;
424*4882a593Smuzhiyun 	int type = $1 >> 16;
425*4882a593Smuzhiyun 	int config = $1 & 255;
426*4882a593Smuzhiyun 
427*4882a593Smuzhiyun 	list = alloc_list();
428*4882a593Smuzhiyun 	ABORT_ON(!list);
429*4882a593Smuzhiyun 	ABORT_ON(parse_events_add_numeric(_parse_state, list, type, config, NULL));
430*4882a593Smuzhiyun 	$$ = list;
431*4882a593Smuzhiyun }
432*4882a593Smuzhiyun |
433*4882a593Smuzhiyun PE_VALUE_SYM_TOOL sep_slash_slash_dc
434*4882a593Smuzhiyun {
435*4882a593Smuzhiyun 	struct list_head *list;
436*4882a593Smuzhiyun 
437*4882a593Smuzhiyun 	list = alloc_list();
438*4882a593Smuzhiyun 	ABORT_ON(!list);
439*4882a593Smuzhiyun 	ABORT_ON(parse_events_add_tool(_parse_state, list, $1));
440*4882a593Smuzhiyun 	$$ = list;
441*4882a593Smuzhiyun }
442*4882a593Smuzhiyun 
443*4882a593Smuzhiyun event_legacy_cache:
444*4882a593Smuzhiyun PE_NAME_CACHE_TYPE '-' PE_NAME_CACHE_OP_RESULT '-' PE_NAME_CACHE_OP_RESULT opt_event_config
445*4882a593Smuzhiyun {
446*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
447*4882a593Smuzhiyun 	struct parse_events_error *error = parse_state->error;
448*4882a593Smuzhiyun 	struct list_head *list;
449*4882a593Smuzhiyun 	int err;
450*4882a593Smuzhiyun 
451*4882a593Smuzhiyun 	list = alloc_list();
452*4882a593Smuzhiyun 	ABORT_ON(!list);
453*4882a593Smuzhiyun 	err = parse_events_add_cache(list, &parse_state->idx, $1, $3, $5, error, $6);
454*4882a593Smuzhiyun 	parse_events_terms__delete($6);
455*4882a593Smuzhiyun 	free($1);
456*4882a593Smuzhiyun 	free($3);
457*4882a593Smuzhiyun 	free($5);
458*4882a593Smuzhiyun 	if (err) {
459*4882a593Smuzhiyun 		free_list_evsel(list);
460*4882a593Smuzhiyun 		YYABORT;
461*4882a593Smuzhiyun 	}
462*4882a593Smuzhiyun 	$$ = list;
463*4882a593Smuzhiyun }
464*4882a593Smuzhiyun |
465*4882a593Smuzhiyun PE_NAME_CACHE_TYPE '-' PE_NAME_CACHE_OP_RESULT opt_event_config
466*4882a593Smuzhiyun {
467*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
468*4882a593Smuzhiyun 	struct parse_events_error *error = parse_state->error;
469*4882a593Smuzhiyun 	struct list_head *list;
470*4882a593Smuzhiyun 	int err;
471*4882a593Smuzhiyun 
472*4882a593Smuzhiyun 	list = alloc_list();
473*4882a593Smuzhiyun 	ABORT_ON(!list);
474*4882a593Smuzhiyun 	err = parse_events_add_cache(list, &parse_state->idx, $1, $3, NULL, error, $4);
475*4882a593Smuzhiyun 	parse_events_terms__delete($4);
476*4882a593Smuzhiyun 	free($1);
477*4882a593Smuzhiyun 	free($3);
478*4882a593Smuzhiyun 	if (err) {
479*4882a593Smuzhiyun 		free_list_evsel(list);
480*4882a593Smuzhiyun 		YYABORT;
481*4882a593Smuzhiyun 	}
482*4882a593Smuzhiyun 	$$ = list;
483*4882a593Smuzhiyun }
484*4882a593Smuzhiyun |
485*4882a593Smuzhiyun PE_NAME_CACHE_TYPE opt_event_config
486*4882a593Smuzhiyun {
487*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
488*4882a593Smuzhiyun 	struct parse_events_error *error = parse_state->error;
489*4882a593Smuzhiyun 	struct list_head *list;
490*4882a593Smuzhiyun 	int err;
491*4882a593Smuzhiyun 
492*4882a593Smuzhiyun 	list = alloc_list();
493*4882a593Smuzhiyun 	ABORT_ON(!list);
494*4882a593Smuzhiyun 	err = parse_events_add_cache(list, &parse_state->idx, $1, NULL, NULL, error, $2);
495*4882a593Smuzhiyun 	parse_events_terms__delete($2);
496*4882a593Smuzhiyun 	free($1);
497*4882a593Smuzhiyun 	if (err) {
498*4882a593Smuzhiyun 		free_list_evsel(list);
499*4882a593Smuzhiyun 		YYABORT;
500*4882a593Smuzhiyun 	}
501*4882a593Smuzhiyun 	$$ = list;
502*4882a593Smuzhiyun }
503*4882a593Smuzhiyun 
504*4882a593Smuzhiyun event_legacy_mem:
505*4882a593Smuzhiyun PE_PREFIX_MEM PE_VALUE '/' PE_VALUE ':' PE_MODIFIER_BP sep_dc
506*4882a593Smuzhiyun {
507*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
508*4882a593Smuzhiyun 	struct list_head *list;
509*4882a593Smuzhiyun 	int err;
510*4882a593Smuzhiyun 
511*4882a593Smuzhiyun 	list = alloc_list();
512*4882a593Smuzhiyun 	ABORT_ON(!list);
513*4882a593Smuzhiyun 	err = parse_events_add_breakpoint(list, &parse_state->idx,
514*4882a593Smuzhiyun 					  $2, $6, $4);
515*4882a593Smuzhiyun 	free($6);
516*4882a593Smuzhiyun 	if (err) {
517*4882a593Smuzhiyun 		free(list);
518*4882a593Smuzhiyun 		YYABORT;
519*4882a593Smuzhiyun 	}
520*4882a593Smuzhiyun 	$$ = list;
521*4882a593Smuzhiyun }
522*4882a593Smuzhiyun |
523*4882a593Smuzhiyun PE_PREFIX_MEM PE_VALUE '/' PE_VALUE sep_dc
524*4882a593Smuzhiyun {
525*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
526*4882a593Smuzhiyun 	struct list_head *list;
527*4882a593Smuzhiyun 
528*4882a593Smuzhiyun 	list = alloc_list();
529*4882a593Smuzhiyun 	ABORT_ON(!list);
530*4882a593Smuzhiyun 	if (parse_events_add_breakpoint(list, &parse_state->idx,
531*4882a593Smuzhiyun 					$2, NULL, $4)) {
532*4882a593Smuzhiyun 		free(list);
533*4882a593Smuzhiyun 		YYABORT;
534*4882a593Smuzhiyun 	}
535*4882a593Smuzhiyun 	$$ = list;
536*4882a593Smuzhiyun }
537*4882a593Smuzhiyun |
538*4882a593Smuzhiyun PE_PREFIX_MEM PE_VALUE ':' PE_MODIFIER_BP sep_dc
539*4882a593Smuzhiyun {
540*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
541*4882a593Smuzhiyun 	struct list_head *list;
542*4882a593Smuzhiyun 	int err;
543*4882a593Smuzhiyun 
544*4882a593Smuzhiyun 	list = alloc_list();
545*4882a593Smuzhiyun 	ABORT_ON(!list);
546*4882a593Smuzhiyun 	err = parse_events_add_breakpoint(list, &parse_state->idx,
547*4882a593Smuzhiyun 					  $2, $4, 0);
548*4882a593Smuzhiyun 	free($4);
549*4882a593Smuzhiyun 	if (err) {
550*4882a593Smuzhiyun 		free(list);
551*4882a593Smuzhiyun 		YYABORT;
552*4882a593Smuzhiyun 	}
553*4882a593Smuzhiyun 	$$ = list;
554*4882a593Smuzhiyun }
555*4882a593Smuzhiyun |
556*4882a593Smuzhiyun PE_PREFIX_MEM PE_VALUE sep_dc
557*4882a593Smuzhiyun {
558*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
559*4882a593Smuzhiyun 	struct list_head *list;
560*4882a593Smuzhiyun 
561*4882a593Smuzhiyun 	list = alloc_list();
562*4882a593Smuzhiyun 	ABORT_ON(!list);
563*4882a593Smuzhiyun 	if (parse_events_add_breakpoint(list, &parse_state->idx,
564*4882a593Smuzhiyun 					$2, NULL, 0)) {
565*4882a593Smuzhiyun 		free(list);
566*4882a593Smuzhiyun 		YYABORT;
567*4882a593Smuzhiyun 	}
568*4882a593Smuzhiyun 	$$ = list;
569*4882a593Smuzhiyun }
570*4882a593Smuzhiyun 
571*4882a593Smuzhiyun event_legacy_tracepoint:
572*4882a593Smuzhiyun tracepoint_name opt_event_config
573*4882a593Smuzhiyun {
574*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
575*4882a593Smuzhiyun 	struct parse_events_error *error = parse_state->error;
576*4882a593Smuzhiyun 	struct list_head *list;
577*4882a593Smuzhiyun 	int err;
578*4882a593Smuzhiyun 
579*4882a593Smuzhiyun 	list = alloc_list();
580*4882a593Smuzhiyun 	ABORT_ON(!list);
581*4882a593Smuzhiyun 	if (error)
582*4882a593Smuzhiyun 		error->idx = @1.first_column;
583*4882a593Smuzhiyun 
584*4882a593Smuzhiyun 	err = parse_events_add_tracepoint(list, &parse_state->idx, $1.sys, $1.event,
585*4882a593Smuzhiyun 					error, $2);
586*4882a593Smuzhiyun 
587*4882a593Smuzhiyun 	parse_events_terms__delete($2);
588*4882a593Smuzhiyun 	free($1.sys);
589*4882a593Smuzhiyun 	free($1.event);
590*4882a593Smuzhiyun 	if (err) {
591*4882a593Smuzhiyun 		free(list);
592*4882a593Smuzhiyun 		YYABORT;
593*4882a593Smuzhiyun 	}
594*4882a593Smuzhiyun 	$$ = list;
595*4882a593Smuzhiyun }
596*4882a593Smuzhiyun 
597*4882a593Smuzhiyun tracepoint_name:
598*4882a593Smuzhiyun PE_NAME '-' PE_NAME ':' PE_NAME
599*4882a593Smuzhiyun {
600*4882a593Smuzhiyun 	struct tracepoint_name tracepoint;
601*4882a593Smuzhiyun 
602*4882a593Smuzhiyun 	ABORT_ON(asprintf(&tracepoint.sys, "%s-%s", $1, $3) < 0);
603*4882a593Smuzhiyun 	tracepoint.event = $5;
604*4882a593Smuzhiyun 	free($1);
605*4882a593Smuzhiyun 	free($3);
606*4882a593Smuzhiyun 	$$ = tracepoint;
607*4882a593Smuzhiyun }
608*4882a593Smuzhiyun |
609*4882a593Smuzhiyun PE_NAME ':' PE_NAME
610*4882a593Smuzhiyun {
611*4882a593Smuzhiyun 	struct tracepoint_name tracepoint = {$1, $3};
612*4882a593Smuzhiyun 
613*4882a593Smuzhiyun 	$$ = tracepoint;
614*4882a593Smuzhiyun }
615*4882a593Smuzhiyun 
616*4882a593Smuzhiyun event_legacy_numeric:
617*4882a593Smuzhiyun PE_VALUE ':' PE_VALUE opt_event_config
618*4882a593Smuzhiyun {
619*4882a593Smuzhiyun 	struct list_head *list;
620*4882a593Smuzhiyun 	int err;
621*4882a593Smuzhiyun 
622*4882a593Smuzhiyun 	list = alloc_list();
623*4882a593Smuzhiyun 	ABORT_ON(!list);
624*4882a593Smuzhiyun 	err = parse_events_add_numeric(_parse_state, list, (u32)$1, $3, $4);
625*4882a593Smuzhiyun 	parse_events_terms__delete($4);
626*4882a593Smuzhiyun 	if (err) {
627*4882a593Smuzhiyun 		free(list);
628*4882a593Smuzhiyun 		YYABORT;
629*4882a593Smuzhiyun 	}
630*4882a593Smuzhiyun 	$$ = list;
631*4882a593Smuzhiyun }
632*4882a593Smuzhiyun 
633*4882a593Smuzhiyun event_legacy_raw:
634*4882a593Smuzhiyun PE_RAW opt_event_config
635*4882a593Smuzhiyun {
636*4882a593Smuzhiyun 	struct list_head *list;
637*4882a593Smuzhiyun 	int err;
638*4882a593Smuzhiyun 
639*4882a593Smuzhiyun 	list = alloc_list();
640*4882a593Smuzhiyun 	ABORT_ON(!list);
641*4882a593Smuzhiyun 	err = parse_events_add_numeric(_parse_state, list, PERF_TYPE_RAW, $1, $2);
642*4882a593Smuzhiyun 	parse_events_terms__delete($2);
643*4882a593Smuzhiyun 	if (err) {
644*4882a593Smuzhiyun 		free(list);
645*4882a593Smuzhiyun 		YYABORT;
646*4882a593Smuzhiyun 	}
647*4882a593Smuzhiyun 	$$ = list;
648*4882a593Smuzhiyun }
649*4882a593Smuzhiyun 
650*4882a593Smuzhiyun event_bpf_file:
651*4882a593Smuzhiyun PE_BPF_OBJECT opt_event_config
652*4882a593Smuzhiyun {
653*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
654*4882a593Smuzhiyun 	struct list_head *list;
655*4882a593Smuzhiyun 	int err;
656*4882a593Smuzhiyun 
657*4882a593Smuzhiyun 	list = alloc_list();
658*4882a593Smuzhiyun 	ABORT_ON(!list);
659*4882a593Smuzhiyun 	err = parse_events_load_bpf(parse_state, list, $1, false, $2);
660*4882a593Smuzhiyun 	parse_events_terms__delete($2);
661*4882a593Smuzhiyun 	free($1);
662*4882a593Smuzhiyun 	if (err) {
663*4882a593Smuzhiyun 		free(list);
664*4882a593Smuzhiyun 		YYABORT;
665*4882a593Smuzhiyun 	}
666*4882a593Smuzhiyun 	$$ = list;
667*4882a593Smuzhiyun }
668*4882a593Smuzhiyun |
669*4882a593Smuzhiyun PE_BPF_SOURCE opt_event_config
670*4882a593Smuzhiyun {
671*4882a593Smuzhiyun 	struct list_head *list;
672*4882a593Smuzhiyun 	int err;
673*4882a593Smuzhiyun 
674*4882a593Smuzhiyun 	list = alloc_list();
675*4882a593Smuzhiyun 	ABORT_ON(!list);
676*4882a593Smuzhiyun 	err = parse_events_load_bpf(_parse_state, list, $1, true, $2);
677*4882a593Smuzhiyun 	parse_events_terms__delete($2);
678*4882a593Smuzhiyun 	if (err) {
679*4882a593Smuzhiyun 		free(list);
680*4882a593Smuzhiyun 		YYABORT;
681*4882a593Smuzhiyun 	}
682*4882a593Smuzhiyun 	$$ = list;
683*4882a593Smuzhiyun }
684*4882a593Smuzhiyun 
685*4882a593Smuzhiyun opt_event_config:
686*4882a593Smuzhiyun '/' event_config '/'
687*4882a593Smuzhiyun {
688*4882a593Smuzhiyun 	$$ = $2;
689*4882a593Smuzhiyun }
690*4882a593Smuzhiyun |
691*4882a593Smuzhiyun '/' '/'
692*4882a593Smuzhiyun {
693*4882a593Smuzhiyun 	$$ = NULL;
694*4882a593Smuzhiyun }
695*4882a593Smuzhiyun |
696*4882a593Smuzhiyun {
697*4882a593Smuzhiyun 	$$ = NULL;
698*4882a593Smuzhiyun }
699*4882a593Smuzhiyun 
700*4882a593Smuzhiyun opt_pmu_config:
701*4882a593Smuzhiyun '/' event_config '/'
702*4882a593Smuzhiyun {
703*4882a593Smuzhiyun 	$$ = $2;
704*4882a593Smuzhiyun }
705*4882a593Smuzhiyun |
706*4882a593Smuzhiyun '/' '/'
707*4882a593Smuzhiyun {
708*4882a593Smuzhiyun 	$$ = NULL;
709*4882a593Smuzhiyun }
710*4882a593Smuzhiyun 
711*4882a593Smuzhiyun start_terms: event_config
712*4882a593Smuzhiyun {
713*4882a593Smuzhiyun 	struct parse_events_state *parse_state = _parse_state;
714*4882a593Smuzhiyun 	if (parse_state->terms) {
715*4882a593Smuzhiyun 		parse_events_terms__delete ($1);
716*4882a593Smuzhiyun 		YYABORT;
717*4882a593Smuzhiyun 	}
718*4882a593Smuzhiyun 	parse_state->terms = $1;
719*4882a593Smuzhiyun }
720*4882a593Smuzhiyun 
721*4882a593Smuzhiyun event_config:
722*4882a593Smuzhiyun event_config ',' event_term
723*4882a593Smuzhiyun {
724*4882a593Smuzhiyun 	struct list_head *head = $1;
725*4882a593Smuzhiyun 	struct parse_events_term *term = $3;
726*4882a593Smuzhiyun 
727*4882a593Smuzhiyun 	if (!head) {
728*4882a593Smuzhiyun 		parse_events_term__delete(term);
729*4882a593Smuzhiyun 		YYABORT;
730*4882a593Smuzhiyun 	}
731*4882a593Smuzhiyun 	list_add_tail(&term->list, head);
732*4882a593Smuzhiyun 	$$ = $1;
733*4882a593Smuzhiyun }
734*4882a593Smuzhiyun |
735*4882a593Smuzhiyun event_term
736*4882a593Smuzhiyun {
737*4882a593Smuzhiyun 	struct list_head *head = malloc(sizeof(*head));
738*4882a593Smuzhiyun 	struct parse_events_term *term = $1;
739*4882a593Smuzhiyun 
740*4882a593Smuzhiyun 	ABORT_ON(!head);
741*4882a593Smuzhiyun 	INIT_LIST_HEAD(head);
742*4882a593Smuzhiyun 	list_add_tail(&term->list, head);
743*4882a593Smuzhiyun 	$$ = head;
744*4882a593Smuzhiyun }
745*4882a593Smuzhiyun 
746*4882a593Smuzhiyun event_term:
747*4882a593Smuzhiyun PE_RAW
748*4882a593Smuzhiyun {
749*4882a593Smuzhiyun 	struct parse_events_term *term;
750*4882a593Smuzhiyun 
751*4882a593Smuzhiyun 	ABORT_ON(parse_events_term__num(&term, PARSE_EVENTS__TERM_TYPE_CONFIG,
752*4882a593Smuzhiyun 					NULL, $1, false, &@1, NULL));
753*4882a593Smuzhiyun 	$$ = term;
754*4882a593Smuzhiyun }
755*4882a593Smuzhiyun |
756*4882a593Smuzhiyun PE_NAME '=' PE_NAME
757*4882a593Smuzhiyun {
758*4882a593Smuzhiyun 	struct parse_events_term *term;
759*4882a593Smuzhiyun 
760*4882a593Smuzhiyun 	if (parse_events_term__str(&term, PARSE_EVENTS__TERM_TYPE_USER,
761*4882a593Smuzhiyun 					$1, $3, &@1, &@3)) {
762*4882a593Smuzhiyun 		free($1);
763*4882a593Smuzhiyun 		free($3);
764*4882a593Smuzhiyun 		YYABORT;
765*4882a593Smuzhiyun 	}
766*4882a593Smuzhiyun 	$$ = term;
767*4882a593Smuzhiyun }
768*4882a593Smuzhiyun |
769*4882a593Smuzhiyun PE_NAME '=' PE_VALUE
770*4882a593Smuzhiyun {
771*4882a593Smuzhiyun 	struct parse_events_term *term;
772*4882a593Smuzhiyun 
773*4882a593Smuzhiyun 	if (parse_events_term__num(&term, PARSE_EVENTS__TERM_TYPE_USER,
774*4882a593Smuzhiyun 					$1, $3, false, &@1, &@3)) {
775*4882a593Smuzhiyun 		free($1);
776*4882a593Smuzhiyun 		YYABORT;
777*4882a593Smuzhiyun 	}
778*4882a593Smuzhiyun 	$$ = term;
779*4882a593Smuzhiyun }
780*4882a593Smuzhiyun |
781*4882a593Smuzhiyun PE_NAME '=' PE_VALUE_SYM_HW
782*4882a593Smuzhiyun {
783*4882a593Smuzhiyun 	struct parse_events_term *term;
784*4882a593Smuzhiyun 	int config = $3 & 255;
785*4882a593Smuzhiyun 
786*4882a593Smuzhiyun 	if (parse_events_term__sym_hw(&term, $1, config)) {
787*4882a593Smuzhiyun 		free($1);
788*4882a593Smuzhiyun 		YYABORT;
789*4882a593Smuzhiyun 	}
790*4882a593Smuzhiyun 	$$ = term;
791*4882a593Smuzhiyun }
792*4882a593Smuzhiyun |
793*4882a593Smuzhiyun PE_NAME
794*4882a593Smuzhiyun {
795*4882a593Smuzhiyun 	struct parse_events_term *term;
796*4882a593Smuzhiyun 
797*4882a593Smuzhiyun 	if (parse_events_term__num(&term, PARSE_EVENTS__TERM_TYPE_USER,
798*4882a593Smuzhiyun 					$1, 1, true, &@1, NULL)) {
799*4882a593Smuzhiyun 		free($1);
800*4882a593Smuzhiyun 		YYABORT;
801*4882a593Smuzhiyun 	}
802*4882a593Smuzhiyun 	$$ = term;
803*4882a593Smuzhiyun }
804*4882a593Smuzhiyun |
805*4882a593Smuzhiyun PE_VALUE_SYM_HW
806*4882a593Smuzhiyun {
807*4882a593Smuzhiyun 	struct parse_events_term *term;
808*4882a593Smuzhiyun 	int config = $1 & 255;
809*4882a593Smuzhiyun 
810*4882a593Smuzhiyun 	ABORT_ON(parse_events_term__sym_hw(&term, NULL, config));
811*4882a593Smuzhiyun 	$$ = term;
812*4882a593Smuzhiyun }
813*4882a593Smuzhiyun |
814*4882a593Smuzhiyun PE_TERM '=' PE_NAME
815*4882a593Smuzhiyun {
816*4882a593Smuzhiyun 	struct parse_events_term *term;
817*4882a593Smuzhiyun 
818*4882a593Smuzhiyun 	if (parse_events_term__str(&term, (int)$1, NULL, $3, &@1, &@3)) {
819*4882a593Smuzhiyun 		free($3);
820*4882a593Smuzhiyun 		YYABORT;
821*4882a593Smuzhiyun 	}
822*4882a593Smuzhiyun 	$$ = term;
823*4882a593Smuzhiyun }
824*4882a593Smuzhiyun |
825*4882a593Smuzhiyun PE_TERM '=' PE_VALUE
826*4882a593Smuzhiyun {
827*4882a593Smuzhiyun 	struct parse_events_term *term;
828*4882a593Smuzhiyun 
829*4882a593Smuzhiyun 	ABORT_ON(parse_events_term__num(&term, (int)$1, NULL, $3, false, &@1, &@3));
830*4882a593Smuzhiyun 	$$ = term;
831*4882a593Smuzhiyun }
832*4882a593Smuzhiyun |
833*4882a593Smuzhiyun PE_TERM
834*4882a593Smuzhiyun {
835*4882a593Smuzhiyun 	struct parse_events_term *term;
836*4882a593Smuzhiyun 
837*4882a593Smuzhiyun 	ABORT_ON(parse_events_term__num(&term, (int)$1, NULL, 1, true, &@1, NULL));
838*4882a593Smuzhiyun 	$$ = term;
839*4882a593Smuzhiyun }
840*4882a593Smuzhiyun |
841*4882a593Smuzhiyun PE_NAME array '=' PE_NAME
842*4882a593Smuzhiyun {
843*4882a593Smuzhiyun 	struct parse_events_term *term;
844*4882a593Smuzhiyun 
845*4882a593Smuzhiyun 	if (parse_events_term__str(&term, PARSE_EVENTS__TERM_TYPE_USER,
846*4882a593Smuzhiyun 					$1, $4, &@1, &@4)) {
847*4882a593Smuzhiyun 		free($1);
848*4882a593Smuzhiyun 		free($4);
849*4882a593Smuzhiyun 		free($2.ranges);
850*4882a593Smuzhiyun 		YYABORT;
851*4882a593Smuzhiyun 	}
852*4882a593Smuzhiyun 	term->array = $2;
853*4882a593Smuzhiyun 	$$ = term;
854*4882a593Smuzhiyun }
855*4882a593Smuzhiyun |
856*4882a593Smuzhiyun PE_NAME array '=' PE_VALUE
857*4882a593Smuzhiyun {
858*4882a593Smuzhiyun 	struct parse_events_term *term;
859*4882a593Smuzhiyun 
860*4882a593Smuzhiyun 	if (parse_events_term__num(&term, PARSE_EVENTS__TERM_TYPE_USER,
861*4882a593Smuzhiyun 					$1, $4, false, &@1, &@4)) {
862*4882a593Smuzhiyun 		free($1);
863*4882a593Smuzhiyun 		free($2.ranges);
864*4882a593Smuzhiyun 		YYABORT;
865*4882a593Smuzhiyun 	}
866*4882a593Smuzhiyun 	term->array = $2;
867*4882a593Smuzhiyun 	$$ = term;
868*4882a593Smuzhiyun }
869*4882a593Smuzhiyun |
870*4882a593Smuzhiyun PE_DRV_CFG_TERM
871*4882a593Smuzhiyun {
872*4882a593Smuzhiyun 	struct parse_events_term *term;
873*4882a593Smuzhiyun 	char *config = strdup($1);
874*4882a593Smuzhiyun 
875*4882a593Smuzhiyun 	ABORT_ON(!config);
876*4882a593Smuzhiyun 	if (parse_events_term__str(&term, PARSE_EVENTS__TERM_TYPE_DRV_CFG,
877*4882a593Smuzhiyun 					config, $1, &@1, NULL)) {
878*4882a593Smuzhiyun 		free($1);
879*4882a593Smuzhiyun 		free(config);
880*4882a593Smuzhiyun 		YYABORT;
881*4882a593Smuzhiyun 	}
882*4882a593Smuzhiyun 	$$ = term;
883*4882a593Smuzhiyun }
884*4882a593Smuzhiyun 
885*4882a593Smuzhiyun array:
886*4882a593Smuzhiyun '[' array_terms ']'
887*4882a593Smuzhiyun {
888*4882a593Smuzhiyun 	$$ = $2;
889*4882a593Smuzhiyun }
890*4882a593Smuzhiyun |
891*4882a593Smuzhiyun PE_ARRAY_ALL
892*4882a593Smuzhiyun {
893*4882a593Smuzhiyun 	$$.nr_ranges = 0;
894*4882a593Smuzhiyun 	$$.ranges = NULL;
895*4882a593Smuzhiyun }
896*4882a593Smuzhiyun 
897*4882a593Smuzhiyun array_terms:
898*4882a593Smuzhiyun array_terms ',' array_term
899*4882a593Smuzhiyun {
900*4882a593Smuzhiyun 	struct parse_events_array new_array;
901*4882a593Smuzhiyun 
902*4882a593Smuzhiyun 	new_array.nr_ranges = $1.nr_ranges + $3.nr_ranges;
903*4882a593Smuzhiyun 	new_array.ranges = realloc($1.ranges,
904*4882a593Smuzhiyun 				sizeof(new_array.ranges[0]) *
905*4882a593Smuzhiyun 				new_array.nr_ranges);
906*4882a593Smuzhiyun 	ABORT_ON(!new_array.ranges);
907*4882a593Smuzhiyun 	memcpy(&new_array.ranges[$1.nr_ranges], $3.ranges,
908*4882a593Smuzhiyun 	       $3.nr_ranges * sizeof(new_array.ranges[0]));
909*4882a593Smuzhiyun 	free($3.ranges);
910*4882a593Smuzhiyun 	$$ = new_array;
911*4882a593Smuzhiyun }
912*4882a593Smuzhiyun |
913*4882a593Smuzhiyun array_term
914*4882a593Smuzhiyun 
915*4882a593Smuzhiyun array_term:
916*4882a593Smuzhiyun PE_VALUE
917*4882a593Smuzhiyun {
918*4882a593Smuzhiyun 	struct parse_events_array array;
919*4882a593Smuzhiyun 
920*4882a593Smuzhiyun 	array.nr_ranges = 1;
921*4882a593Smuzhiyun 	array.ranges = malloc(sizeof(array.ranges[0]));
922*4882a593Smuzhiyun 	ABORT_ON(!array.ranges);
923*4882a593Smuzhiyun 	array.ranges[0].start = $1;
924*4882a593Smuzhiyun 	array.ranges[0].length = 1;
925*4882a593Smuzhiyun 	$$ = array;
926*4882a593Smuzhiyun }
927*4882a593Smuzhiyun |
928*4882a593Smuzhiyun PE_VALUE PE_ARRAY_RANGE PE_VALUE
929*4882a593Smuzhiyun {
930*4882a593Smuzhiyun 	struct parse_events_array array;
931*4882a593Smuzhiyun 
932*4882a593Smuzhiyun 	ABORT_ON($3 < $1);
933*4882a593Smuzhiyun 	array.nr_ranges = 1;
934*4882a593Smuzhiyun 	array.ranges = malloc(sizeof(array.ranges[0]));
935*4882a593Smuzhiyun 	ABORT_ON(!array.ranges);
936*4882a593Smuzhiyun 	array.ranges[0].start = $1;
937*4882a593Smuzhiyun 	array.ranges[0].length = $3 - $1 + 1;
938*4882a593Smuzhiyun 	$$ = array;
939*4882a593Smuzhiyun }
940*4882a593Smuzhiyun 
941*4882a593Smuzhiyun sep_dc: ':' |
942*4882a593Smuzhiyun 
943*4882a593Smuzhiyun sep_slash_slash_dc: '/' '/' | ':' |
944*4882a593Smuzhiyun 
945*4882a593Smuzhiyun %%
946*4882a593Smuzhiyun 
947*4882a593Smuzhiyun void parse_events_error(YYLTYPE *loc, void *parse_state,
948*4882a593Smuzhiyun 			void *scanner __maybe_unused,
949*4882a593Smuzhiyun 			char const *msg __maybe_unused)
950*4882a593Smuzhiyun {
951*4882a593Smuzhiyun 	parse_events_evlist_error(parse_state, loc->last_column, "parser error");
952*4882a593Smuzhiyun }
953