summaryrefslogtreecommitdiff
path: root/apps/plugins/databox/editparser.c
diff options
context:
space:
mode:
Diffstat (limited to 'apps/plugins/databox/editparser.c')
-rw-r--r--apps/plugins/databox/editparser.c203
1 files changed, 203 insertions, 0 deletions
diff --git a/apps/plugins/databox/editparser.c b/apps/plugins/databox/editparser.c
new file mode 100644
index 0000000000..d2fcbc4e6d
--- /dev/null
+++ b/apps/plugins/databox/editparser.c
@@ -0,0 +1,203 @@
1/***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
9 *
10 * Copyright (C) 2005 by Michiel van der Kolk
11 *
12 * All files in this archive are subject to the GNU General Public License.
13 * See the file COPYING in the source tree root for full license agreement.
14 *
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
17 *
18 ****************************************************************************/
19#include "databox.h"
20#include "edittoken.h"
21#include "editparser.h"
22
23struct token *currenttoken,*lasttoken,*tokenstream;
24int currentindex;
25int lparencount,acceptedmask;
26int tokensleft;
27int invalid;
28int invalid_mode;
29
30void check_accepted(struct token *tstream, int count) {
31 parse_stream(tstream,count+1,INVALID_EXPERT);
32}
33
34void parse_stream(struct token *tstream, int count, int inv_mode) {
35 invalid_mode=inv_mode;
36 acceptedmask=0;
37 lparencount=0;
38 tokensleft=count;
39 currentindex=0;
40 invalid=0;
41 tokenstream=tstream;
42 currenttoken=&tokenstream[currentindex];
43 parseMExpr();
44}
45
46int check_tokenstream(struct token *tstream, int inv_mode) {
47 int inval=0;
48 int i;
49 parse_stream(tstream,-1,inv_mode);
50 inval=invalid;
51 while( (inv_mode==INVALID_STRIP||inv_mode==INVALID_MARK) && invalid)
52 parse_stream(tstream,-1,inv_mode);
53 i=0;
54 while(tstream[i].kind!=TOKEN_EOF)
55 if(tstream[i++].kind==TOKEN_INVALID) {
56 inval=1;
57 break;
58 }
59 return inval==0;
60}
61
62
63void parse_accept_rparen(void) {
64 if(!tokensleft) return;
65 if(lparencount) {
66 acceptedmask|=ACCEPT_RPAREN;
67 }
68}
69
70void parse_accept(int bitmask) {
71 if(!tokensleft) return;
72 acceptedmask|=bitmask;
73 if(lparencount) {
74 acceptedmask&=~ACCEPT_EOF;
75 }
76}
77
78void parse_checktoken() {
79 int ok=0;
80 if(!tokensleft) return;
81 lasttoken=currenttoken;
82 switch(lasttoken->kind) {
83 case TOKEN_EOF:
84 ok=acceptedmask&ACCEPT_EOF;
85 break;
86 case TOKEN_NOT:
87 ok=acceptedmask&ACCEPT_NOT;
88 break;
89 case TOKEN_AND:
90 case TOKEN_OR:
91 ok=acceptedmask&ACCEPT_BOOLOP;
92 break;
93 case TOKEN_GT:
94 case TOKEN_GTE:
95 case TOKEN_LT:
96 case TOKEN_LTE:
97 case TOKEN_NE:
98 case TOKEN_EQ:
99 ok=acceptedmask&ACCEPT_NUMOP;
100 break;
101 case TOKEN_EQUALS:
102 case TOKEN_CONTAINS:
103 ok=acceptedmask&ACCEPT_STROP;
104 break;
105 case TOKEN_STRING:
106 case TOKEN_STRINGIDENTIFIER:
107 ok=acceptedmask&ACCEPT_STRARG;
108 break;
109 case TOKEN_NUM:
110 case TOKEN_NUMIDENTIFIER:
111 ok=acceptedmask&ACCEPT_NUMARG;
112 break;
113 case TOKEN_LPAREN:
114 ok=acceptedmask&ACCEPT_LPAREN;
115 if(ok) lparencount++;
116 break;
117 case TOKEN_RPAREN:
118 ok=acceptedmask&ACCEPT_RPAREN;
119 if(ok) lparencount--;
120 break;
121 case TOKEN_INVALID:
122 if(invalid_mode!=INVALID_STRIP)
123 ok=1;
124 break;
125 }
126 tokensleft--;
127 if(lasttoken->kind==TOKEN_EOF)
128 tokensleft=0;
129 if(!ok&&tokensleft) {
130 // delete token
131 int i=currentindex;
132 //printf("Syntax error. accepted: 0x%x index:%d token: %d %s\n",acceptedmask,currentindex,currenttoken->kind,tokentostring(currenttoken));
133 switch (invalid_mode) {
134 case INVALID_STRIP:
135 do {
136 rb->memcpy(currenttoken,&tokenstream[++i],sizeof(struct token));;
137 currenttoken=&tokenstream[i];
138 } while (currenttoken->kind!=TOKEN_EOF);
139 currenttoken=&tokenstream[currentindex];
140 break;
141 case INVALID_MARK:
142 currenttoken->kind=TOKEN_INVALID;
143 break;
144 }
145 tokensleft=0;
146 invalid=1;
147 }
148 if(tokensleft) {
149 currenttoken=&tokenstream[++currentindex];
150 acceptedmask=0;
151 }
152}
153
154void parseCompareNum() {
155 parse_accept(ACCEPT_NUMOP);
156 parse_checktoken();
157 parse_accept(ACCEPT_NUMARG);
158 parse_checktoken();
159}
160
161void parseCompareString() {
162 parse_accept(ACCEPT_STROP);
163 parse_checktoken();
164 parse_accept(ACCEPT_STRARG);
165 parse_checktoken();
166}
167
168void parseExpr() {
169 if(!tokensleft) return;
170 parse_accept(ACCEPT_NOT|ACCEPT_LPAREN|ACCEPT_NUMARG|ACCEPT_STRARG);
171 parse_checktoken();
172 switch(lasttoken->kind) {
173 case TOKEN_NOT:
174 parseExpr();
175 break;
176 case TOKEN_LPAREN:
177 parseMExpr();
178 break;
179 case TOKEN_NUM:
180 case TOKEN_NUMIDENTIFIER:
181 parseCompareNum();
182 break;
183 case TOKEN_STRING:
184 case TOKEN_STRINGIDENTIFIER:
185 parseCompareString();
186 break;
187 }
188}
189
190void parseMExpr() {
191 parseExpr();
192 parse_accept_rparen();
193 parse_accept(ACCEPT_BOOLOP|ACCEPT_EOF);
194 parse_checktoken();
195 while(lasttoken->kind==TOKEN_OR || lasttoken->kind == TOKEN_AND) {
196 parseExpr();
197 parse_accept_rparen();
198 parse_accept(ACCEPT_BOOLOP|ACCEPT_EOF);
199 parse_checktoken();
200 if(!tokensleft)
201 return;
202 }
203}