Parse-Eyapp

 view release on metacpan or  search on metacpan

lib/Parse/Eyapp/eyapplanguageref.pod  view on Meta::CPAN

To solve a shift-reduce conflict between a production C<A --E<gt> SOMETHING>
and a token C<'a'> you can follow this procedure:

=over

=item 1. Edit the C<.output> file

=item 2. Search for the state where the conflict between the production and the token
is. In our example it looks like:

 pl@nereida:~/src/perl/YappWithDefaultAction/examples$ sed -ne '56,65p' ambiguities.output
 State 5:

        exp -> exp . '-' exp    (Rule 2)
        exp -> exp '-' exp .    (Rule 2)

        '-'     shift, and go to state 3

        '-'     [reduce using rule 2 (exp)]
        $default        reduce using rule 2 (exp)

=item 3. Inside the state there has to be a production of the type C<A --E<gt> SOMETHING.> 
(with the dot at the end)
indicating that a reduction must take place. There has to be also another production 
of the form C<A --E<gt> prefix . suffix>, where suffix can I<start> with the involved
token C<'a'>. 

=item 4. Decide what action shift or reduce matches the kind of trees you want.
In this example we want C<NUM - NUM - NUM> to produce a tree like
C<MINUS(MINUS(NUM, NUM), NUM)> and not C<MINUS(NUM, MINUS(NUM, NUM))>. We want the 
conflict in C<exp - exp.- NUM> to be solved in favor of the reduction
by C<exp: exp '-' exp>. 
This is achieved by declaring C<%left '-'>. 

=back

=head2 Error Recovery

The token name C<error> is reserved for error handling. This name can
be used in grammar productions; it suggests places where errors are
expected, and recovery can take place:

     line:
       '\n'         { undef }
       | exp '\n'   { print "$_[1]\n" if defined($_[1]); $_[1] }
       | error  '\n'
           {
             $_[0]->YYErrok;
             undef
           }


The parser pops its stack until
it enters a state where the token C<error> is legal. It then shifts
the token C<error> and proceeds to discard tokens until finding 
one that is acceptable. In the example
all the tokens until finding a C<'\n'> will be skipped. 
If no special error productions have been specified,
the processing will halt.

In order to prevent a cascade of error messages, the parser, after
detecting an error, remains in error state until three tokens have been
successfully read and shifted. If an error is detected when the parser
is already in error state, no message is given, and the input token is
quietly deleted. The method C<YYErrok> used in the example 
communicates to the parser
that a satisfactory recovery has been reached 
and that it can safely emit new error
messages.

You cannot have a literal I<'error'> in your grammar as it would
confuse the driver with the I<error> token. Use a symbolic token instead.

=head1 THE TAIL

The tail section contains Perl code. Usually it is empty, but you
can if you want put here your own lexical analyzer and 
error management subroutines.
An example of this is in
files C<examples/eyapplanguageref/List3_tree_d_sem.yp> (the grammar)
and C<use_list3_tree_d_dem.pl> (the client).

=head1 THE LEXICAL ANALYZER

The Lexical Analyzer 
is called each time the parser needs a new token.
It is called with only one argument (the parser object)
and returns a pair 
containing the next token and its associated attribute.

The fact that is a method of the parser object means that the parser
methods are accessible inside the lexical analyzer.

When the lexical analyzer reaches the end of input, it must return the
pair C<('', undef)>

=head2 Automatic Generation of Lexical Analyzers

By default a lexical analyzer is built.
The C<eyapp> option C<-l>
can be used to inhibit the generation of 
the default lexical analyzer. In such case,
one must be explictly provided.


=head3 No token Definitions

When no token definitions are given in the head section, 
the default lexical analyzer simply assumes
that the token is the string literal. See this example in 
file C<examples/lexergeneration/simple.yp>:

  pl@nereida:~/LEyapp/examples/lexergeneration$ cat simple.yp
  %%
  A:    a
      | A d
  ;
  %%


The grammar does not describes the lexical analyzer nor the error default subroutine.



( run in 0.740 second using v1.01-cache-2.11-cpan-e93a5daba3e )