1 %option prefix="perf_bpf_filter_"
2 %option noyywrap
3 
4 %{
5 #include <stdio.h>
6 #include <stdlib.h>
7 #include <linux/perf_event.h>
8 
9 #include "bpf-filter.h"
10 #include "bpf-filter-bison.h"
11 
sample(unsigned long sample_flag)12 static int sample(unsigned long sample_flag)
13 {
14 	perf_bpf_filter_lval.sample.type = sample_flag;
15 	perf_bpf_filter_lval.sample.part = 0;
16 	return BFT_SAMPLE;
17 }
18 
sample_part(unsigned long sample_flag,int part)19 static int sample_part(unsigned long sample_flag, int part)
20 {
21 	perf_bpf_filter_lval.sample.type = sample_flag;
22 	perf_bpf_filter_lval.sample.part = part;
23 	return BFT_SAMPLE;
24 }
25 
operator(enum perf_bpf_filter_op op)26 static int operator(enum perf_bpf_filter_op op)
27 {
28 	perf_bpf_filter_lval.op = op;
29 	return BFT_OP;
30 }
31 
value(int base)32 static int value(int base)
33 {
34 	long num;
35 
36 	errno = 0;
37 	num = strtoul(perf_bpf_filter_text, NULL, base);
38 	if (errno)
39 		return BFT_ERROR;
40 
41 	perf_bpf_filter_lval.num = num;
42 	return BFT_NUM;
43 }
44 
constant(int val)45 static int constant(int val)
46 {
47 	perf_bpf_filter_lval.num = val;
48 	return BFT_NUM;
49 }
50 
error(const char * str)51 static int error(const char *str)
52 {
53 	printf("perf_bpf_filter: Unexpected filter %s: %s\n", str, perf_bpf_filter_text);
54 	return BFT_ERROR;
55 }
56 
57 %}
58 
59 num_dec		[0-9]+
60 num_hex		0[Xx][0-9a-fA-F]+
61 space		[ \t]+
62 ident		[_a-zA-Z][_a-zA-Z0-9]+
63 
64 %%
65 
66 {num_dec}	{ return value(10); }
67 {num_hex}	{ return value(16); }
68 {space}		{ }
69 
70 ip		{ return sample(PERF_SAMPLE_IP); }
71 id		{ return sample(PERF_SAMPLE_ID); }
72 tid		{ return sample(PERF_SAMPLE_TID); }
73 pid		{ return sample_part(PERF_SAMPLE_TID, 1); }
74 cpu		{ return sample(PERF_SAMPLE_CPU); }
75 time		{ return sample(PERF_SAMPLE_TIME); }
76 addr		{ return sample(PERF_SAMPLE_ADDR); }
77 period		{ return sample(PERF_SAMPLE_PERIOD); }
78 txn		{ return sample(PERF_SAMPLE_TRANSACTION); }
79 weight		{ return sample(PERF_SAMPLE_WEIGHT); }
80 weight1		{ return sample_part(PERF_SAMPLE_WEIGHT_STRUCT, 1); }
81 weight2		{ return sample_part(PERF_SAMPLE_WEIGHT_STRUCT, 2); }
82 weight3		{ return sample_part(PERF_SAMPLE_WEIGHT_STRUCT, 3); }
83 ins_lat		{ return sample_part(PERF_SAMPLE_WEIGHT_STRUCT, 2); } /* alias for weight2 */
84 p_stage_cyc	{ return sample_part(PERF_SAMPLE_WEIGHT_STRUCT, 3); } /* alias for weight3 */
85 retire_lat	{ return sample_part(PERF_SAMPLE_WEIGHT_STRUCT, 3); } /* alias for weight3 */
86 phys_addr	{ return sample(PERF_SAMPLE_PHYS_ADDR); }
87 code_pgsz	{ return sample(PERF_SAMPLE_CODE_PAGE_SIZE); }
88 data_pgsz	{ return sample(PERF_SAMPLE_DATA_PAGE_SIZE); }
89 mem_op		{ return sample_part(PERF_SAMPLE_DATA_SRC, 1); }
90 mem_lvlnum	{ return sample_part(PERF_SAMPLE_DATA_SRC, 2); }
91 mem_lvl		{ return sample_part(PERF_SAMPLE_DATA_SRC, 2); } /* alias for mem_lvlnum */
92 mem_snoop	{ return sample_part(PERF_SAMPLE_DATA_SRC, 3); } /* include snoopx */
93 mem_remote	{ return sample_part(PERF_SAMPLE_DATA_SRC, 4); }
94 mem_lock	{ return sample_part(PERF_SAMPLE_DATA_SRC, 5); }
95 mem_dtlb	{ return sample_part(PERF_SAMPLE_DATA_SRC, 6); }
96 mem_blk		{ return sample_part(PERF_SAMPLE_DATA_SRC, 7); }
97 mem_hops	{ return sample_part(PERF_SAMPLE_DATA_SRC, 8); }
98 
99 "=="		{ return operator(PBF_OP_EQ); }
100 "!="		{ return operator(PBF_OP_NEQ); }
101 ">"		{ return operator(PBF_OP_GT); }
102 "<"		{ return operator(PBF_OP_LT); }
103 ">="		{ return operator(PBF_OP_GE); }
104 "<="		{ return operator(PBF_OP_LE); }
105 "&"		{ return operator(PBF_OP_AND); }
106 
107 na		{ return constant(PERF_MEM_OP_NA); }
108 load		{ return constant(PERF_MEM_OP_LOAD); }
109 store		{ return constant(PERF_MEM_OP_STORE); }
110 pfetch		{ return constant(PERF_MEM_OP_PFETCH); }
111 exec		{ return constant(PERF_MEM_OP_EXEC); }
112 
113 l1		{ return constant(PERF_MEM_LVLNUM_L1); }
114 l2		{ return constant(PERF_MEM_LVLNUM_L2); }
115 l3		{ return constant(PERF_MEM_LVLNUM_L3); }
116 l4		{ return constant(PERF_MEM_LVLNUM_L4); }
117 cxl		{ return constant(PERF_MEM_LVLNUM_CXL); }
118 io		{ return constant(PERF_MEM_LVLNUM_IO); }
119 any_cache	{ return constant(PERF_MEM_LVLNUM_ANY_CACHE); }
120 lfb		{ return constant(PERF_MEM_LVLNUM_LFB); }
121 ram		{ return constant(PERF_MEM_LVLNUM_RAM); }
122 pmem		{ return constant(PERF_MEM_LVLNUM_PMEM); }
123 
124 none		{ return constant(PERF_MEM_SNOOP_NONE); }
125 hit		{ return constant(PERF_MEM_SNOOP_HIT); }
126 miss		{ return constant(PERF_MEM_SNOOP_MISS); }
127 hitm		{ return constant(PERF_MEM_SNOOP_HITM); }
128 fwd		{ return constant(PERF_MEM_SNOOPX_FWD); }
129 peer		{ return constant(PERF_MEM_SNOOPX_PEER); }
130 
131 remote		{ return constant(PERF_MEM_REMOTE_REMOTE); }
132 
133 locked		{ return constant(PERF_MEM_LOCK_LOCKED); }
134 
135 l1_hit		{ return constant(PERF_MEM_TLB_L1 | PERF_MEM_TLB_HIT); }
136 l1_miss		{ return constant(PERF_MEM_TLB_L1 | PERF_MEM_TLB_MISS); }
137 l2_hit		{ return constant(PERF_MEM_TLB_L2 | PERF_MEM_TLB_HIT); }
138 l2_miss		{ return constant(PERF_MEM_TLB_L2 | PERF_MEM_TLB_MISS); }
139 any_hit		{ return constant(PERF_MEM_TLB_HIT); }
140 any_miss	{ return constant(PERF_MEM_TLB_MISS); }
141 walk		{ return constant(PERF_MEM_TLB_WK); }
142 os		{ return constant(PERF_MEM_TLB_OS); }
143 fault		{ return constant(PERF_MEM_TLB_OS); } /* alias for os */
144 
145 by_data		{ return constant(PERF_MEM_BLK_DATA); }
146 by_addr		{ return constant(PERF_MEM_BLK_ADDR); }
147 
148 hops0		{ return constant(PERF_MEM_HOPS_0); }
149 hops1		{ return constant(PERF_MEM_HOPS_1); }
150 hops2		{ return constant(PERF_MEM_HOPS_2); }
151 hops3		{ return constant(PERF_MEM_HOPS_3); }
152 
153 ","		{ return ','; }
154 "||"		{ return BFT_LOGICAL_OR; }
155 
156 {ident}		{ return error("ident"); }
157 .		{ return error("input"); }
158 
159 %%
160