Skip Menu |

This queue is for tickets about the Parse-RecDescent CPAN distribution.

Report information
The Basics
Id: 63120
Status: open
Priority: 0/
Queue: Parse-RecDescent

People
Owner: Nobody in particular
Requestors: mhhollomon [...] gmail.com
Cc:
AdminCc:

Bug Information
Severity: Important
Broken in: 1.965001
Fixed in: (no value)



Subject: $thisline is easily confused - even with resync
Running the attached test script "linetest.pl", the output is ... $ ./linetest.pl Show quoted text
>>> a 1 >>> a 2 >>> b 3 >>> c 9 >>> a 6 >>> a 7 >>> c 8 >>> b 9 >>> c 15 >>> a 7 >>> a 8 >>> c 14 >>> c 15
Applying the attached patch, the output is: $ ./linetest.pl Show quoted text
>>> a 1 >>> a 2 >>> b 3 >>> c 3 >>> a 5 >>> a 6 >>> c 7 >>> b 9 >>> c 9 >>> a 11 >>> a 12 >>> c 13 >>> c 15
which, if nothing else, is at least monotonically non-decreasing. I'm not sure the %counter_cache really buys anything. And given that it is a package lexical, every running parser will share it. So, if I start a "sub-parser" inside an action, the cache will contain a strange mix of data.
Subject: linetest.pl
#!/usr/bin/perl -w use strict; use warnings; use lib './blib/lib'; use Parse::RecDescent; #$::RD_TRACE = 1; my $p = Parse::RecDescent->new(<<'GRAMMAR'); TOP: token(s) /\z/ token: 'a' { print ">>> a $thisline\n" } | 'b' { print ">>> b $thisline\n"; $text = "c\n\na\na\nc\n" . $text; Parse::RecDescent::LineCounter::resync($thisline) } | 'c' { print ">>> c $thisline\n"; } GRAMMAR defined($p) or die "FAILED to create parser\n"; defined($p->TOP("a\na\nb\nb\nc\n")) or die "FAILED to parse.";
Subject: linecounter.patch
*** RecDescent.pm.orig 2010-11-18 11:36:02.722933000 -0500 --- RecDescent.pm 2010-11-18 11:37:28.723483400 -0500 *************** sub FETCH *** 113,119 **** unless (exists $counter_cache{$from}) { $parser->{lastlinenum} = $parser->{offsetlinenum} ! - Parse::RecDescent::_linecount(substr($parser->{fulltext},$from)) + 1; $counter_cache{$from} = $parser->{lastlinenum}; } --- 113,119 ---- unless (exists $counter_cache{$from}) { $parser->{lastlinenum} = $parser->{offsetlinenum} ! - Parse::RecDescent::_linecount(${$_[0]->{text}}) + 1; $counter_cache{$from} = $parser->{lastlinenum}; } *************** sub resync # ($linecounter) *** 139,144 **** --- 139,145 ---- + 1; $parser->{offsetlinenum} += $parser->{lastlinenum} - $apparently; + %counter_cache = (); return 1; } *************** A subrule which appears in a production *** 3372,3378 **** attempt to match the named rule at that point in the text being parsed. If the named subrule is not defined when requested the production containing it immediately fails (unless it was "autostubbed" - see ! L<Autostubbing>). A rule may (recursively) call itself as a subrule, but I<not> as the left-most item in any of its productions (since such recursions are usually --- 3373,3379 ---- attempt to match the named rule at that point in the text being parsed. If the named subrule is not defined when requested the production containing it immediately fails (unless it was "autostubbed" - see ! L<"Autostubbing">). A rule may (recursively) call itself as a subrule, but I<not> as the left-most item in any of its productions (since such recursions are usually
Version 1.966_002 contains a fix for the %counter_cache issue that you've noted. I'm working on some changes to allow lexing to be split from parsing, at which time $thisline and friends are going to be revisited.