File Coverage

blib/lib/Shishi/Node.pm
Criterion Covered Total %
statement 55 57 96.4
branch 17 32 53.1
condition n/a
subroutine 6 6 100.0
pod 0 4 0.0
total 78 99 78.7


line stmt bran cond sub pod time code
1             package Shishi::Node;
2 1     1   449 use Shishi::Decision;
  1         3  
  1         58  
3 1     1   5 use strict;
  1         2  
  1         1169  
4              
5             sub new {
6 3     3 0 10 my $class = shift;
7 3         51 bless {
8             creator => shift,
9             parents => 0,
10             decisions => [],
11             }, $class;
12             }
13              
14             my %match = (
15             char => sub { my ($d, $tr) = @_; my $targ = $d->{target}; $$tr =~ s/^$targ//; },
16             text => sub { my ($d, $tr) = @_; my $targ = $d->{target}; $$tr =~ s/^$targ//; },
17             token => sub { my ($d, $tr) = @_; my $tk = chr $d->{token}; $$tr =~ s/^$tk//; },
18             any=> sub { my ($d, $tr) = @_; $$tr =~ s/.//; },
19             skip=> sub { my ($d, $tr) = @_; $$tr =~ s/.//; },
20             end => sub { my ($d, $tr) = @_; length $$tr == 0; },
21             true => sub {1},
22             code => sub { my ($d, $tr, $parser) = @_;
23             print "Performing code\n" if $Shishi::Debug;
24             $d->{code}->($parser, $tr);
25             },
26             );
27              
28             sub execute {
29 4     4 0 6 my $self = shift;
30 4         4 my $parser = shift;
31 4         5 my $match_object = shift;
32 4         5 my @decs = @{$self->{decisions}};
  4         9  
33              
34 19 50       39 recurse:
35              
36             print "Executing node $self, parser is $parser, mo is $match_object\n" if $Shishi::Debug;
37 19         25 for my $d (@decs) {
38 18         44 my $text = $match_object->parse_text();
39 18 50       34 print "This decision is $d\n" if $Shishi::Debug;
40 18         27 my $targ = $d->{target};
41 18         21 my $type = $d->{type};
42 18         19 my $action = $d->{action};
43 18 50       28 print "Trying decision $type -> $targ on $text ($d)\n"
44             if $Shishi::Debug;
45 18 50       38 die "Unknown match type $type" unless exists $match{$type};
46 18 100       34 next unless $match{$type}->($d, \$text, $parser); # Match
47 13 50       25 print "$type -> $targ succeeded, action $action\n" if $Shishi::Debug;
48 13         34 $match_object->parse_text($text);
49 13         14 my $rc;
50 13 100       26 if ($action == ACTION_CONTINUE) {
    50          
    0          
51             # Put stuff on stack.
52 11 50       19 print "Matched, continuing, recursing\n" if $Shishi::Debug;
53 11         12 push @{$match_object->{been}}, { node => $self, text => $text, d => $d};
  11         49  
54 11         18 $self = $d->{next_node};
55 11         10 @decs = @{$self->{decisions}};
  11         47  
56 11         129 goto recurse;
57             } elsif ($action == ACTION_FINISH) {
58 2 50       4 print "Finishing\n" if $Shishi::Debug;
59 2         13 return 1;
60             } elsif ($action == ACTION_FAIL) {
61 0 0       0 print "Bailing!\n" if $Shishi::Debug;
62 0         0 return -1;
63             }
64             }
65 6 50       23 print "I need to pop the stack here at end\n" if $Shishi::Debug;
66 6 100       5 if (my $pframe = pop @{$match_object->{been}}) {
  6         18  
67 4         6 $self = $pframe->{node};
68 4         9 my $text = $pframe->{text};
69 4         10 $match_object->parse_text($text);
70 4         8 @decs = $self->decisions;
71 4         5 while (1) {
72 4 50       19 die "Internal error: decision not found" unless @decs;
73 4         5 my $x = shift @decs;
74 4 50       11 last if $x == $pframe->{d};
75             }
76 4         20 goto recurse;
77             }
78 2         13 return 0;
79             }
80              
81             sub add_decision {
82 4     4 0 6 my $self = shift; push @{$self->{decisions}}, shift; return $self;
  4         5  
  4         9  
  4         9  
83             }
84              
85 4     4 0 4 sub decisions { @{$_[0]->{decisions}} }
  4         12  
86              
87             1;