12 void yyerror (char const *);
14 int regex_cmp(char* s, char* r);
15 struct tree* tree_malloc(int type);
16 void print_tree(struct tree* t, int ind);
28 } st; /* subtree type */
31 struct tree* c; /* condition */
32 struct tree* i; /* if */
33 struct tree* e; /* else */
40 } cond; /* binary operator */
79 struct tree* input_tree;
94 %token <str> KW_PIPE KW_MAIL KW_COPY
95 %token '(' ')' '{' '}' ';'
99 %left <n> EQ NEQ GE LE '<' '>' RE NRE
122 input: /* empty */ { $$ = input_tree = NULL; }
123 | command input { $$ = tree_malloc(ST_BLOCK);
124 $$->pt.block.head = $1;
125 $$->pt.block.tail = $2;
131 command: ';' { $$ = tree_malloc(ST_EMPTY); }
132 | '{' command next '}' {
133 $$ = tree_malloc(ST_BLOCK);
134 $$->pt.block.head = $2;
135 $$->pt.block.tail = $3;
137 | '{' '}' { $$ = tree_malloc(ST_EMPTY); }
140 | arrow ';' { $$ = $1}
145 next: /* empty */ {$$ = NULL}
151 cif: KW_IF cond command KW_ELSE command {
152 $$ = tree_malloc(ST_IF);
157 | KW_IF cond command {
158 $$ = tree_malloc(ST_IF);
166 $$ = tree_malloc(ST_COND);
167 $$->pt.cond.left = $2;
168 $$->pt.cond.right = NULL;
173 $$ = tree_malloc(ST_COND);
174 $$->pt.cond.left = $1;
175 $$->pt.cond.right = $3;
180 $$ = tree_malloc(ST_COND);
181 $$->pt.cond.left = $1;
182 $$->pt.cond.right = $3;
187 $$ = tree_malloc(ST_COND);
188 $$->pt.cond.left = $1;
189 $$->pt.cond.right = $3;
193 | '(' cond ')' { $$ = $2; }
194 | ass_right rop ass_right {
195 $$ = tree_malloc(ST_COND);
196 $$->pt.cond.left = $1;
197 $$->pt.cond.right = $3;
214 $$ = tree_malloc(ST_ASS);
216 $$->pt.ass.left = tree_malloc(ST_LEAF);
217 $$->pt.ass.left->pt.leaf.type = L_VAR;
218 $$->pt.ass.left->pt.leaf.value.s = $1;
220 $$->pt.ass.right = $3;
225 $$ = tree_malloc(ST_LEAF);
226 $$->pt.leaf.type = L_NUM;
227 $$->pt.leaf.value.n = $1;
230 $$ = tree_malloc(ST_LEAF);
231 $$->pt.leaf.type = L_VAR;
232 $$->pt.leaf.value.s = $1;
235 $$ = tree_malloc(ST_LEAF);
236 $$->pt.leaf.type = L_CONST;
237 $$->pt.leaf.value.s = $1;
241 arrow: left ARROW right ass_right {
242 $$ = tree_malloc(ST_ARROW);
244 $$->pt.arrow.kw_left = $1;
245 $$->pt.arrow.kw_right = $3;
249 left: /* empty */ {$$=NULL}
250 | KW_COPY { $$ = "copy" }
254 right: /* empty */ {$$ = NULL}
255 | KW_PIPE { $$ = "pipe" }
256 | KW_MAIL { $$ = "mail" }
260 | ass_right '.' ass_right {
261 $$ = tree_malloc(ST_OP);
264 $$->pt.op.right = $3;
271 tree_malloc(int type)
274 temp = xmalloc(sizeof (struct tree));
281 regex_cmp(char* s, char* r)
286 int ovector[OVECCOUNT];
288 brum = pcre_compile(r,0,&error,&erroroffset,NULL);
292 int res = pcre_exec(brum,NULL,s,strlen(s),0,0,ovector,OVECCOUNT);
299 yyerror (char const *s)
301 fprintf (stderr, "Line %d: %s\n", line, s);
305 print_ind(int num, char c)
309 for (i = 0; i < num; i++){
315 print_tree(struct tree* t, int ind)
324 print_tree(t->pt.tif.c,ind+1);
327 print_tree(t->pt.tif.i,ind+1);
330 print_tree(t->pt.tif.e,ind+1);
333 #define UPPER(a) ((a) >> 8)
334 #define LOWER(a) ((a) & 0xFF)
335 print_tree(t->pt.cond.left, ind+1);
338 if (UPPER(t->pt.cond.op) > 0)
339 putchar(UPPER(t->pt.cond.op));
340 putchar(LOWER(t->pt.cond.op));
342 print_tree(t->pt.cond.right, ind+1);
345 print_tree(t->pt.block.head,ind);
346 print_tree(t->pt.block.tail,ind);
349 print_tree(t->pt.ass.left, ind+1);
352 print_tree(t->pt.ass.right, ind+1);
356 switch (t->pt.leaf.type){
360 puts(t->pt.leaf.value.s);
363 printf("%d\n",t->pt.leaf.value.n);
368 if (t->pt.arrow.kw_left){
369 print_ind(ind+1, ' ');
370 puts(t->pt.arrow.kw_left);
374 if (t->pt.arrow.kw_right){
375 print_ind(ind+1, ' ');
376 puts(t->pt.arrow.kw_right);
378 print_tree(t->pt.arrow.s,ind+1);
381 print_tree(t->pt.op.left, ind+1);
383 putchar(t->pt.op.op);
385 print_tree(t->pt.op.right, ind+1);
401 print_tree(input_tree,0);