Skip to content

Commit

Permalink
Merge pull request #110 from philwills/negative-predicate-doesnt-advance
Browse files Browse the repository at this point in the history
Explain how to advance with negative syntactic predicate
  • Loading branch information
sirthias committed Feb 18, 2015
2 parents 62dee52 + d2db943 commit be254e1
Showing 1 changed file with 26 additions and 0 deletions.
26 changes: 26 additions & 0 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -399,6 +399,9 @@ a | b
have had on the value stack are cleared out, the resulting rule type is therefore always ``Rule0``,
independently of the type of the underlying rule.

Note that ``&`` not causing the parser to make any progress can have surprising implications in repeating
contructs, see `Stack overflow when using the or operator`_ for more details.

----

!a
Expand All @@ -407,6 +410,9 @@ a | b
out all effects that the underlying rule might have had on the value stack. The resulting rule type is therefore
always ``Rule0``, independently of the type of the underlying rule.

Note that ``&`` not causing the parser to make any progress can have surprising implications in repeating
contructs, see `Stack overflow when using the or operator`_ for more details.

----

optional(a)
Expand Down Expand Up @@ -848,6 +854,26 @@ specific alternatives first are the canonical solutions.
If your parser is not behaving the way you expect it to watch out for this "wrong ordering" problem, which might be
not that easy to spot in more complicated rule structures.

Stack overflow when using the ``!`` or ``&`` operator
-----------------------------------------------------

The syntactic predicate combinators, ``!`` and ``&``, do not cause the parser to advance so combining them with a repeating
repeating combinator (``zeroOrMore``, ``oneOrMore``, ``xxx.times``) will lead to a stack overflow as the parser repeatedly
runs the syntactic predicate on the same point in the data it's trying to parse.

For example

.. code:: Scala
def foo = rule { capture(zeroOrMore( !',' )) }
will overflow the stack when run on anything except commas, while

.. code:: Scala
def foo = rule { capture(zeroOrMore( !',' ~ ANY )) }
will capture all input until it reaches a comma.

Unchecked Mutable State
-----------------------
Expand Down

0 comments on commit be254e1

Please sign in to comment.