[antlr-interest] Repeated explicit evaluation of the tree in ANTLR3.

pganelin ganelin at mail.com
Tue Aug 7 05:06:52 PDT 2007


After I switched from ANTLR V2 to ANTL v3 I found that I can not walk 
repeatedly over the same tree multiple times within tree walker. To 
illustrate the problem I choose (Visual) Basic as a well known 
interpreted language.

Let's consider DO WHILE loop. Suppose that I am “lazy” and do not worry 
too much about the performance. Instead of creating intermediate p-code 
for the program execution I just keep my ANTLR tree as a run time 
representation. For “while evaluation” it means walking the tree all 
over again during the execution phase of the program. In ANTLR2 I had 
something like this

class BasicTree extends TreeParser;

doWhile:
      #(WHILE e:. b:.)
      {
         boolean cond=false;
         do {
             boolean cond = expression(e);
             if (!cond) break;
             block(b);
         }
         while(true);
      }
;

expression returns [boolean cond]:
#(EXPR …)
;

block:
#(SLIST …)
;


where “expression” evaluates the Boolean condition "and block" executes 
the statements.

Please note that I can trick the ANTLR2 into repeatedly walking the tree 
by explicitly passing the first parameter – sub tree to walk.

In ANTLR v3 I do not have the option of passing subtree as the first 
parameter of grammar rule. Instead I need to create the token stream in 
advance and pass it in tree constructor. I tried some ugly hack like this

doWhile:
      ^(WHILE e=. b=.)
      {
         boolean cond=false;
         do {
	push($e);
             boolean cond = expression();
	pop()
             if (!cond) break;
	push($b);
             block();
	pop()
         }
         while (cond != 0);     }
;

expression:
^(EXPR …)
;
block:
^(SLIST …)

     private void pop() {
         input =stack.pop());
     }

     private void push(Tree e) {
         stack.push(input);
         CommonTreeNodeStream nodes = new CommonTreeNodeStream(e);
         nodes.setTokenStream(input.getTokenStream());
         input = nodes;

     }

but failed to make it work. Also I suspect it would be extremely 
inefficient even in my case.

Maybe I should be able to push and pop input stream state? I was not 
able to figure out how to do it.

Any suggestions how to solve this problem in ANTLR3 would be greatly 
appreciated.

Thanks,
Pavel







More information about the antlr-interest mailing list