1/*
2 * BPF asm code lexer
3 *
4 * This program is free software; you can distribute it and/or modify
5 * it under the terms of the GNU General Public License as published
6 * by the Free Software Foundation; either version 2 of the License,
7 * or (at your option) any later version.
8 *
9 * Syntax kept close to:
10 *
11 * Steven McCanne and Van Jacobson. 1993. The BSD packet filter: a new
12 * architecture for user-level packet capture. In Proceedings of the
13 * USENIX Winter 1993 Conference Proceedings on USENIX Winter 1993
14 * Conference Proceedings (USENIX'93). USENIX Association, Berkeley,
15 * CA, USA, 2-2.
16 *
17 * Copyright 2013 Daniel Borkmann <borkmann@redhat.com>
18 * Licensed under the GNU General Public License, version 2.0 (GPLv2)
19 */
20
21%{
22
23#include <stdio.h>
24#include <stdint.h>
25#include <stdlib.h>
26
27#include "bpf_exp.yacc.h"
28
29extern void yyerror(const char *str);
30
31%}
32
33%option align
34%option ecs
35
36%option nounput
37%option noreject
38%option noinput
39%option noyywrap
40
41%option 8bit
42%option caseless
43%option yylineno
44
45%%
46
47"ldb"		{ return OP_LDB; }
48"ldh"		{ return OP_LDH; }
49"ld"		{ return OP_LD; }
50"ldi"		{ return OP_LDI; }
51"ldx"		{ return OP_LDX; }
52"ldxi"		{ return OP_LDXI; }
53"ldxb"		{ return OP_LDXB; }
54"st"		{ return OP_ST; }
55"stx"		{ return OP_STX; }
56"jmp"		{ return OP_JMP; }
57"ja"		{ return OP_JMP; }
58"jeq"		{ return OP_JEQ; }
59"jneq"		{ return OP_JNEQ; }
60"jne"		{ return OP_JNEQ; }
61"jlt"		{ return OP_JLT; }
62"jle"		{ return OP_JLE; }
63"jgt"		{ return OP_JGT; }
64"jge"		{ return OP_JGE; }
65"jset"		{ return OP_JSET; }
66"add"		{ return OP_ADD; }
67"sub"		{ return OP_SUB; }
68"mul"		{ return OP_MUL; }
69"div"		{ return OP_DIV; }
70"mod"		{ return OP_MOD; }
71"neg"		{ return OP_NEG; }
72"and"		{ return OP_AND; }
73"xor"		{ return OP_XOR; }
74"or"		{ return OP_OR; }
75"lsh"		{ return OP_LSH; }
76"rsh"		{ return OP_RSH; }
77"ret"		{ return OP_RET; }
78"tax"		{ return OP_TAX; }
79"txa"		{ return OP_TXA; }
80
81"#"?("len")	{ return K_PKT_LEN; }
82"#"?("proto")	{ return K_PROTO; }
83"#"?("type")	{ return K_TYPE; }
84"#"?("poff")	{ return K_POFF; }
85"#"?("ifidx")	{ return K_IFIDX; }
86"#"?("nla")	{ return K_NLATTR; }
87"#"?("nlan")	{ return K_NLATTR_NEST; }
88"#"?("mark")	{ return K_MARK; }
89"#"?("queue")	{ return K_QUEUE; }
90"#"?("hatype")	{ return K_HATYPE; }
91"#"?("rxhash")	{ return K_RXHASH; }
92"#"?("cpu")	{ return K_CPU; }
93"#"?("vlan_tci")	{ return K_VLAN_TCI; }
94"#"?("vlan_pr")		{ return K_VLAN_AVAIL; }
95"#"?("vlan_avail")	{ return K_VLAN_AVAIL; }
96"#"?("vlan_tpid")	{ return K_VLAN_TPID; }
97"#"?("rand")	{ return K_RAND; }
98
99":"		{ return ':'; }
100","		{ return ','; }
101"#"		{ return '#'; }
102"%"		{ return '%'; }
103"["		{ return '['; }
104"]"		{ return ']'; }
105"("		{ return '('; }
106")"		{ return ')'; }
107"x"		{ return 'x'; }
108"a"		{ return 'a'; }
109"+"		{ return '+'; }
110"M"		{ return 'M'; }
111"*"		{ return '*'; }
112"&"		{ return '&'; }
113
114([0][x][a-fA-F0-9]+) {
115			yylval.number = strtoul(yytext, NULL, 16);
116			return number;
117		}
118([0][b][0-1]+)	{
119			yylval.number = strtol(yytext + 2, NULL, 2);
120			return number;
121		}
122(([0])|([-+]?[1-9][0-9]*)) {
123			yylval.number = strtol(yytext, NULL, 10);
124			return number;
125		}
126([0][0-9]+)	{
127			yylval.number = strtol(yytext + 1, NULL, 8);
128			return number;
129		}
130[a-zA-Z_][a-zA-Z0-9_]+ {
131			yylval.label = strdup(yytext);
132			return label;
133		}
134
135"/*"([^\*]|\*[^/])*"*/"		{ /* NOP */ }
136";"[^\n]*			{ /* NOP */ }
137^#.*				{ /* NOP */ }
138[ \t]+				{ /* NOP */ }
139[ \n]+				{ /* NOP */ }
140
141.		{
142			printf("unknown character \'%s\'", yytext);
143			yyerror("lex unknown character");
144		}
145
146%%
147