[antlr-interest] How to handle rewrite of multiple nodes

Simon simonzmail at gmail.com
Tue Mar 29 18:43:27 PDT 2011


Hello all,

I have a grammar that does a rewrite like so:

  bracketedBlock
      : '{' stmts=statement* '}' -> ^(Block $stmts)
      ;

As you can see, the rule is matching multiple statements inside
brackets, like in a typical programming language with blocks - for
example:

   {  echo 'hello';  echo 'world'; }

The problem is that it actually produces a tree like this:

  64: Block
    34: echo
      92: 'world'

Whereas I would expect this:

  64: Block
    34: echo
      92: 'hello'
    34: echo
      92: 'world'

I thought that perhaps the right solution was to add brackets:

  bracketedBlock
      : '{' stmts=(statement*) '}' -> ^(Block $stmts)

However this produces a runtime error when I run the parser:

Antlr.Runtime.Tree.RewriteEmptyStreamException: token stmts
   at Antlr.Runtime.Tree.RewriteRuleElementStream`1._Next()
   at Antlr.Runtime.Tree.RewriteRuleTokenStream.NextNode()

It works fine if I spell out the number of blocks explicitly:

  bracketedBlock
      : '{' s1=statement s2=statement '}' -> ^(Block $s1 $s2)
      ;

So I was wondering if there is a different way to perform a rewrite
rule that would match multiple elements?

In case it is important, the target here is CSharp2.

Many thanks for any help!

Simon


More information about the antlr-interest mailing list