Version 0.006009
[p5sagit/Devel-Declare.git] / lib / Devel / Declare.pm
CommitLineData
94caac6e 1package Devel::Declare;
2
3use strict;
4use warnings;
5use 5.008001;
6
7bf75905 7our $VERSION = '0.006009';
0ba8c7aa 8
9use constant DECLARE_NAME => 1;
10use constant DECLARE_PROTO => 2;
53e3ab32 11use constant DECLARE_NONE => 4;
15d0d014 12use constant DECLARE_PACKAGE => 8+1; # name implicit
0ba8c7aa 13
86c3de80 14use vars qw(%declarators %declarator_handlers @ISA);
94caac6e 15use base qw(DynaLoader);
323ae557 16use Scalar::Util 'set_prototype';
39801454 17use B::Hooks::OP::Check 0.19;
94caac6e 18
19bootstrap Devel::Declare;
20
86c3de80 21@ISA = ();
22
8ec78a85 23initialize();
24
94caac6e 25sub import {
0ba8c7aa 26 my ($class, %args) = @_;
94caac6e 27 my $target = caller;
0ba8c7aa 28 if (@_ == 1) { # "use Devel::Declare;"
29 no strict 'refs';
15d0d014 30 foreach my $name (qw(NAME PROTO NONE PACKAGE)) {
53e3ab32 31 *{"${target}::DECLARE_${name}"} = *{"DECLARE_${name}"};
0ba8c7aa 32 }
33 } else {
34 $class->setup_for($target => \%args);
35 }
94caac6e 36}
37
38sub unimport {
39 my ($class) = @_;
40 my $target = caller;
41 $class->teardown_for($target);
42}
43
44sub setup_for {
45 my ($class, $target, $args) = @_;
46 setup();
0ba8c7aa 47 foreach my $key (keys %$args) {
48 my $info = $args->{$key};
49 my ($flags, $sub);
50 if (ref($info) eq 'ARRAY') {
51 ($flags, $sub) = @$info;
52 } elsif (ref($info) eq 'CODE') {
53 $flags = DECLARE_NAME;
54 $sub = $info;
840ebcbb 55 } elsif (ref($info) eq 'HASH') {
56 $flags = 1;
57 $sub = $info;
0ba8c7aa 58 } else {
840ebcbb 59 die "Info for sub ${key} must be [ \$flags, \$sub ] or \$sub or handler hashref";
0ba8c7aa 60 }
61 $declarators{$target}{$key} = $flags;
62 $declarator_handlers{$target}{$key} = $sub;
63 }
94caac6e 64}
65
66sub teardown_for {
67 my ($class, $target) = @_;
68 delete $declarators{$target};
0ba8c7aa 69 delete $declarator_handlers{$target};
94caac6e 70}
71
94caac6e 72my $temp_name;
0ba8c7aa 73my $temp_save;
94caac6e 74
75sub init_declare {
0f070758 76 my ($usepack, $use, $inpack, $name, $proto, $traits) = @_;
53e3ab32 77 my ($name_h, $XX_h, $extra_code)
9026391e 78 = $declarator_handlers{$usepack}{$use}->(
0f070758 79 $usepack, $use, $inpack, $name, $proto, defined(wantarray), $traits
53e3ab32 80 );
15d0d014 81 ($temp_name, $temp_save) = ([], []);
0ba8c7aa 82 if ($name) {
9026391e 83 $name = "${inpack}::${name}" unless $name =~ /::/;
840ebcbb 84 shadow_sub($name, $name_h);
0ba8c7aa 85 }
86 if ($XX_h) {
840ebcbb 87 shadow_sub("${inpack}::X", $XX_h);
0ba8c7aa 88 }
53e3ab32 89 if (defined wantarray) {
90 return $extra_code || '0;';
91 } else {
92 return;
93 }
94caac6e 94}
95
840ebcbb 96sub shadow_sub {
97 my ($name, $cr) = @_;
98 push(@$temp_name, $name);
99 no strict 'refs';
100 my ($pack, $pname) = ($name =~ m/(.+)::([^:]+)/);
101 push(@$temp_save, $pack->can($pname));
840ebcbb 102 no warnings 'redefine';
103 no warnings 'prototype';
104 *{$name} = $cr;
105 set_in_declare(~~@{$temp_name||[]});
106}
107
94caac6e 108sub done_declare {
109 no strict 'refs';
86c3de80 110 my $name = shift(@{$temp_name||[]});
0ba8c7aa 111 die "done_declare called with no temp_name stack" unless defined($name);
86c3de80 112 my $saved = shift(@$temp_save);
15d0d014 113 $name =~ s/(.*):://;
114 my $temp_pack = $1;
0ba8c7aa 115 delete ${"${temp_pack}::"}{$name};
116 if ($saved) {
117 no warnings 'prototype';
118 *{"${temp_pack}::${name}"} = $saved;
119 }
840ebcbb 120 set_in_declare(~~@{$temp_name||[]});
94caac6e 121}
122
323ae557 123sub build_sub_installer {
124 my ($class, $pack, $name, $proto) = @_;
125 return eval "
126 package ${pack};
127 my \$body;
128 sub ${name} (${proto}) :lvalue {\n"
003ac394 129 .' if (wantarray) {
c5912dc7 130 goto &$body;
003ac394 131 }
132 my $ret = $body->(@_);
86c3de80 133 return $ret;
323ae557 134 };
135 sub { ($body) = @_; };';
136}
137
138sub setup_declarators {
139 my ($class, $pack, $to_setup) = @_;
86c3de80 140 die "${class}->setup_declarators(\$pack, \\\%to_setup)"
141 unless defined($pack) && ref($to_setup) eq 'HASH';
142 my %setup_for_args;
323ae557 143 foreach my $name (keys %$to_setup) {
144 my $info = $to_setup->{$name};
145 my $flags = $info->{flags} || DECLARE_NAME;
146 my $run = $info->{run};
147 my $compile = $info->{compile};
148 my $proto = $info->{proto} || '&';
149 my $sub_proto = $proto;
150 # make all args optional to enable lvalue for DECLARE_NONE
151 $sub_proto =~ s/;//; $sub_proto = ';'.$sub_proto;
86c3de80 152 #my $installer = $class->build_sub_installer($pack, $name, $proto);
153 my $installer = $class->build_sub_installer($pack, $name, '@');
86c3de80 154 $installer->(sub :lvalue {
003ac394 155#{ no warnings 'uninitialized'; warn 'INST: '.join(', ', @_)."\n"; }
c5534496 156 if (@_) {
157 if (ref $_[0] eq 'HASH') {
158 shift;
003ac394 159 if (wantarray) {
160 my @ret = $run->(undef, undef, @_);
161 return @ret;
162 }
c5534496 163 my $r = $run->(undef, undef, @_);
164 return $r;
165 } else {
003ac394 166 return @_[1..$#_];
c5534496 167 }
86c3de80 168 }
169 return my $sv;
170 });
171 $setup_for_args{$name} = [
172 $flags,
173 sub {
0f070758 174 my ($usepack, $use, $inpack, $name, $proto, $shift_hashref, $traits) = @_;
175 my $extra_code = $compile->($name, $proto, $traits);
003ac394 176 my $main_handler = sub { shift if $shift_hashref;
c5534496 177 ("DONE", $run->($name, $proto, @_));
003ac394 178 };
86c3de80 179 my ($name_h, $XX);
180 if (defined $proto) {
181 $name_h = sub :lvalue { return my $sv; };
182 $XX = $main_handler;
c5534496 183 } elsif (defined $name && length $name) {
86c3de80 184 $name_h = $main_handler;
185 }
003ac394 186 $extra_code ||= '';
187 $extra_code = '}, sub {'.$extra_code;
86c3de80 188 return ($name_h, $XX, $extra_code);
189 }
190 ];
323ae557 191 }
86c3de80 192 $class->setup_for($pack, \%setup_for_args);
193}
194
195sub install_declarator {
196 my ($class, $target_pack, $target_name, $flags, $filter, $handler) = @_;
197 $class->setup_declarators($target_pack, {
198 $target_name => {
199 flags => $flags,
200 compile => $filter,
201 run => $handler,
202 }
203 });
323ae557 204}
205
04a8a223 206sub linestr_callback_rv2cv {
207 my ($name, $offset) = @_;
208 $offset += toke_move_past_token($offset);
209 my $pack = get_curstash_name();
210 my $flags = $declarators{$pack}{$name};
211 my ($found_name, $found_proto);
04a8a223 212 if ($flags & DECLARE_NAME) {
213 $offset += toke_skipspace($offset);
214 my $linestr = get_linestr();
215 if (substr($linestr, $offset, 2) eq '::') {
216 substr($linestr, $offset, 2) = '';
217 set_linestr($linestr);
218 }
219 if (my $len = toke_scan_word($offset, $flags & DECLARE_PACKAGE)) {
220 $found_name = substr($linestr, $offset, $len);
221 $offset += $len;
04a8a223 222 }
223 }
224 if ($flags & DECLARE_PROTO) {
225 $offset += toke_skipspace($offset);
226 my $linestr = get_linestr();
227 if (substr($linestr, $offset, 1) eq '(') {
228 my $length = toke_scan_str($offset);
229 $found_proto = get_lex_stuff();
230 clear_lex_stuff();
231 my $replace =
232 ($found_name ? ' ' : '=')
233 .'X'.(' ' x length($found_proto));
234 $linestr = get_linestr();
235 substr($linestr, $offset, $length) = $replace;
236 set_linestr($linestr);
237 $offset += $length;
04a8a223 238 }
239 }
240 my @args = ($pack, $name, $pack, $found_name, $found_proto);
04a8a223 241 $offset += toke_skipspace($offset);
242 my $linestr = get_linestr();
243 if (substr($linestr, $offset, 1) eq '{') {
244 my $ret = init_declare(@args);
245 $offset++;
246 if (defined $ret && length $ret) {
247 substr($linestr, $offset, 0) = $ret;
248 set_linestr($linestr);
249 }
250 } else {
251 init_declare(@args);
252 }
253 #warn "linestr now ${linestr}";
254}
255
569ac469 256sub linestr_callback_const {
04a8a223 257 my ($name, $offset) = @_;
258 my $pack = get_curstash_name();
259 my $flags = $declarators{$pack}{$name};
260 if ($flags & DECLARE_NAME) {
261 $offset += toke_move_past_token($offset);
262 $offset += toke_skipspace($offset);
263 if (toke_scan_word($offset, $flags & DECLARE_PACKAGE)) {
264 my $linestr = get_linestr();
265 substr($linestr, $offset, 0) = '::';
266 set_linestr($linestr);
267 }
268 }
569ac469 269}
270
271sub linestr_callback {
272 my $type = shift;
840ebcbb 273 my $name = $_[0];
274 my $pack = get_curstash_name();
275 my $handlers = $declarator_handlers{$pack}{$name};
276 if (ref $handlers eq 'CODE') {
277 my $meth = "linestr_callback_${type}";
278 __PACKAGE__->can($meth)->(@_);
279 } elsif (ref $handlers eq 'HASH') {
280 if ($handlers->{$type}) {
281 $handlers->{$type}->(@_);
282 }
283 } else {
284 die "PANIC: unknown thing in handlers for $pack $name: $handlers";
285 }
569ac469 286}
287
94caac6e 288=head1 NAME
289
7e31b6e3 290Devel::Declare - Adding keywords to perl, in perl
94caac6e 291
292=head1 SYNOPSIS
293
1795217c 294 use Method::Signatures;
295 # or ...
296 use MooseX::Declare;
297 # etc.
298
299 # Use some new and exciting syntax like:
300 method hello (Str :$who, Int :$age where { $_ > 0 }) {
301 $self->say("Hello ${who}, I am ${age} years old!");
302 }
303
304=head1 DESCRIPTION
305
306L<Devel::Declare> can install subroutines called declarators which locally take
307over Perl's parser, allowing the creation of new syntax.
308
309This document describes how to create a simple declarator.
310
311=head1 USAGE
312
313We'll demonstrate the usage of C<Devel::Declare> with a motivating example: a new
314C<method> keyword, which acts like the builtin C<sub>, but automatically unpacks
315C<$self> and the other arguments.
316
317 package My::Methods;
318 use Devel::Declare;
319
320=head2 Creating a declarator with C<setup_for>
321
322You will typically create
323
324 sub import {
325 my $class = shift;
326 my $caller = caller;
327
328 Devel::Declare->setup_for(
329 $caller,
330 { method => { const => \&parser } }
331 );
332 no strict 'refs';
333 *{$caller.'::method'} = sub (&) {};
334 }
335
336Starting from the end of this import routine, you'll see that we're creating a
337subroutine called C<method> in the caller's namespace. Yes, that's just a normal
338subroutine, and it does nothing at all (yet!) Note the prototype C<(&)> which means
339that the caller would call it like so:
340
341 method {
342 my ($self, $arg1, $arg2) = @_;
343 ...
344 }
345
346However we want to be able to call it like this
347
348 method foo ($arg1, $arg2) {
349 ...
350 }
351
352That's why we call C<setup_for> above, to register the declarator 'method' with a custom
353parser, as per the next section. It acts on an optype, usually C<'const'> as above.
354(Other valid values are C<'check'> and C<'rv2cv'>).
355
356For a simpler way to install new methods, see also L<Devel::Declare::MethodInstaller::Simple>
357
358=head2 Writing a parser subroutine
359
360This subroutine is called at I<compilation> time, and allows you to read the custom
361syntaxes that we want (in a syntax that may or may not be valid core Perl 5) and
362munge it so that the result will be parsed by the C<perl> compiler.
363
364For this example, we're defining some globals for convenience:
365
2ee34f20 366 our ($Declarator, $Offset);
1795217c 367
368Then we define a parser subroutine to handle our declarator. We'll look at this in
369a few chunks.
370
371 sub parser {
372 local ($Declarator, $Offset) = @_;
373
374C<Devel::Declare> provides some very low level utility methods to parse character
375strings. We'll define some useful higher level routines below for convenience,
376and we can use these to parse the various elements in our new syntax.
377
378Notice how our parser subroutine is invoked at compile time,
379when the C<perl> parser is pointed just I<before> the declarator name.
380
381 skip_declarator; # step past 'method'
382 my $name = strip_name; # strip out the name 'foo', if present
383 my $proto = strip_proto; # strip out the prototype '($arg1, $arg2)', if present
384
385Now we can prepare some code to 'inject' into the new subroutine. For example we
386might want the method as above to have C<my ($self, $arg1, $arg2) = @_> injected at
387the beginning of it. We also do some clever stuff with scopes that we'll look
388at shortly.
389
390 my $inject = make_proto_unwrap($proto);
391 if (defined $name) {
392 $inject = scope_injector_call().$inject;
393 }
394 inject_if_block($inject);
395
396We've now managed to change C<method ($arg1, $arg2) { ... }> into C<method {
397injected_code; ... }>. This will compile... but we've lost the name of the
398method!
399
400In a cute (or horrifying, depending on your perspective) trick, we temporarily
401change the definition of the subroutine C<method> itself, to specialise it with
402the C<$name> we stripped, so that it assigns the code block to that name.
403
404Even though the I<next> time C<method> is compiled, it will be
405redefined again, C<perl> caches these definitions in its parse
406tree, so we'll always get the right one!
407
408Note that we also handle the case where there was no name, allowing
409an anonymous method analogous to an anonymous subroutine.
410
411 if (defined $name) {
412 $name = join('::', Devel::Declare::get_curstash_name(), $name)
413 unless ($name =~ /::/);
414 shadow(sub (&) { no strict 'refs'; *{$name} = shift; });
415 } else {
416 shadow(sub (&) { shift });
417 }
418 }
419
420
421=head2 Parser utilities in detail
422
423For simplicity, we're using global variables like C<$Offset> in these examples.
424You may prefer to look at L<Devel::Declare::Context::Simple>, which
425encapsulates the context much more cleanly.
426
427=head3 C<skip_declarator>
428
429This simple parser just moves across a 'token'. The common case is
430to skip the declarator, i.e. to move to the end of the string
431'method' and before the prototype and code block.
432
2ee34f20 433 sub skip_declarator {
434 $Offset += Devel::Declare::toke_move_past_token($Offset);
435 }
1795217c 436
437=head4 C<toke_move_past_token>
438
439This builtin parser simply moves past a 'token' (matching C</[a-zA-Z_]\w*/>)
440It takes an offset into the source document, and skips past the token.
441It returns the number of characters skipped.
442
443=head3 C<strip_name>
444
445This parser skips any whitespace, then scans the next word (again matching a
446'token'). We can then analyse the current line, and manipulate it (using pure
447Perl). In this case we take the name of the method out, and return it.
448
2ee34f20 449 sub strip_name {
450 skipspace;
451 if (my $len = Devel::Declare::toke_scan_word($Offset, 1)) {
452 my $linestr = Devel::Declare::get_linestr();
453 my $name = substr($linestr, $Offset, $len);
454 substr($linestr, $Offset, $len) = '';
455 Devel::Declare::set_linestr($linestr);
456 return $name;
457 }
458 return;
459 }
1795217c 460
461=head4 C<toke_scan_word>
462
463This builtin parser, given an offset into the source document,
464matches a 'token' as above but does not skip. It returns the
465length of the token matched, if any.
466
467=head4 C<get_linestr>
468
469This builtin returns the full text of the current line of the source document.
470
471=head4 C<set_linestr>
472
473This builtin sets the full text of the current line of the source document.
2627a85c 474Beware that injecting a newline into the middle of the line is likely
475to fail in surprising ways. Generally, Perl's parser can rely on the
476`current line' actually being only a single line. Use other kinds of
477whitespace instead, in the code that you inject.
1795217c 478
479=head3 C<skipspace>
480
481This parser skips whitsepace.
482
483 sub skipspace {
484 $Offset += Devel::Declare::toke_skipspace($Offset);
485 }
486
487=head4 C<toke_skipspace>
488
489This builtin parser, given an offset into the source document,
490skips over any whitespace, and returns the number of characters
491skipped.
492
493=head3 C<strip_proto>
494
495This is a more complex parser that checks if it's found something that
496starts with C<'('> and returns everything till the matching C<')'>.
497
2ee34f20 498 sub strip_proto {
499 skipspace;
1795217c 500
2ee34f20 501 my $linestr = Devel::Declare::get_linestr();
502 if (substr($linestr, $Offset, 1) eq '(') {
503 my $length = Devel::Declare::toke_scan_str($Offset);
504 my $proto = Devel::Declare::get_lex_stuff();
505 Devel::Declare::clear_lex_stuff();
506 $linestr = Devel::Declare::get_linestr();
507 substr($linestr, $Offset, $length) = '';
508 Devel::Declare::set_linestr($linestr);
509 return $proto;
510 }
511 return;
512 }
1795217c 513
514=head4 C<toke_scan_str>
515
516This builtin parser uses Perl's own parsing routines to match a "stringlike"
517expression. Handily, this includes bracketed expressions (just think about
518things like C<q(this is a quote)>).
519
520Also it Does The Right Thing with nested delimiters (like C<q(this (is (a) quote))>).
521
78bb475d 522It returns the effective length of the expression matched. Really, what
523it returns is the difference in position between where the string started,
524within the buffer, and where it finished. If the string extended across
525multiple lines then the contents of the buffer may have been completely
526replaced by the new lines, so this position difference is not the same
527thing as the actual length of the expression matched. However, because
528moving backward in the buffer causes problems, the function arranges
529for the effective length to always be positive, padding the start of
530the buffer if necessary.
531
532Use C<get_lex_stuff> to get the actual matched text, the content of
533the string. Because of the behaviour around multiline strings, you
534can't reliably get this from the buffer. In fact, after the function
535returns, you can't rely on any content of the buffer preceding the end
536of the string.
1795217c 537
8449c31f 538If the string being scanned is not well formed (has no closing delimiter),
539C<toke_scan_str> returns C<undef>. In this case you cannot rely on the
540contents of the buffer.
541
1795217c 542=head4 C<get_lex_stuff>
543
544This builtin returns what was matched by C<toke_scan_str>. To avoid segfaults,
545you should call C<clear_lex_stuff> immediately afterwards.
546
547=head2 Munging the subroutine
548
549Let's look at what we need to do in detail.
550
551=head3 C<make_proto_unwrap>
552
553We may have defined our method in different ways, which will result
554in a different value for our prototype, as parsed above. For example:
555
556 method foo { # undefined
557 method foo () { # ''
558 method foo ($arg1) { # '$arg1'
559
560We deal with them as follows, and return the appropriate C<my ($self, ...) = @_;>
561string.
562
2ee34f20 563 sub make_proto_unwrap {
564 my ($proto) = @_;
565 my $inject = 'my ($self';
566 if (defined $proto) {
567 $inject .= ", $proto" if length($proto);
568 $inject .= ') = @_; ';
569 } else {
570 $inject .= ') = shift;';
571 }
572 return $inject;
573 }
1795217c 574
575=head3 C<inject_if_block>
576
577Now we need to inject it after the opening C<'{'> of the method body.
578We can do this with the building blocks we defined above like C<skipspace>
579and C<get_linestr>.
580
2ee34f20 581 sub inject_if_block {
582 my $inject = shift;
583 skipspace;
584 my $linestr = Devel::Declare::get_linestr;
585 if (substr($linestr, $Offset, 1) eq '{') {
586 substr($linestr, $Offset+1, 0) = $inject;
587 Devel::Declare::set_linestr($linestr);
588 }
589 }
94caac6e 590
1795217c 591=head3 C<scope_injector_call>
592
593We want to be able to handle both named and anonymous methods. i.e.
594
595 method foo () { ... }
596 my $meth = method () { ... };
597
598These will then get rewritten as
599
600 method { ... }
601 my $meth = method { ... };
602
603where 'method' is a subroutine that takes a code block. Spot the problem?
604The first one doesn't have a semicolon at the end of it! Unlike 'sub' which
605is a builtin, this is just a normal statement, so we need to terminate it.
6c1cecd4 606Luckily, using C<B::Hooks::EndOfScope>, we can do this!
1795217c 607
6c1cecd4 608 use B::Hooks::EndOfScope;
1795217c 609
610We'll add this to what gets 'injected' at the beginning of the method source.
611
612 sub scope_injector_call {
613 return ' BEGIN { MethodHandlers::inject_scope }; ';
2ee34f20 614 }
1795217c 615
5bcdf810 616So at the beginning of every method, we are passing a callback that will get invoked
1795217c 617at the I<end> of the method's compilation... i.e. exactly then the closing C<'}'>
618is compiled.
619
620 sub inject_scope {
6c1cecd4 621 on_scope_end {
1795217c 622 my $linestr = Devel::Declare::get_linestr;
623 my $offset = Devel::Declare::get_linestr_offset;
624 substr($linestr, $offset, 0) = ';';
625 Devel::Declare::set_linestr($linestr);
6c1cecd4 626 };
2ee34f20 627 }
94caac6e 628
1795217c 629=head2 Shadowing each method.
630
631=head3 C<shadow>
94caac6e 632
1795217c 633We override the current definition of 'method' using C<shadow>.
94caac6e 634
1795217c 635 sub shadow {
636 my $pack = Devel::Declare::get_curstash_name;
637 Devel::Declare::shadow_sub("${pack}::${Declarator}", $_[0]);
2ee34f20 638 }
94caac6e 639
1795217c 640For a named method we invoked like this:
641
642 shadow(sub (&) { no strict 'refs'; *{$name} = shift; });
643
644So in the case of a C<method foo { ... }>, this call would redefine C<method>
645to be a subroutine that exports 'sub foo' as the (munged) contents of C<{...}>.
646
647The case of an anonymous method is also cute:
648
649 shadow(sub (&) { shift });
650
651This means that
652
653 my $meth = method () { ... };
654
655is rewritten with C<method> taking the codeblock, and returning it as is to become
656the value of C<$meth>.
657
658=head4 C<get_curstash_name>
659
660This returns the package name I<currently being compiled>.
661
662=head4 C<shadow_sub>
663
664Handles the details of redefining the subroutine.
665
666=head1 SEE ALSO
667
668One of the best ways to learn C<Devel::Declare> is still to look at
669modules that use it:
670
671L<http://cpants.perl.org/dist/used_by/Devel-Declare>.
94caac6e 672
dcf29eb6 673=head1 AUTHORS
94caac6e 674
502ba90e 675Matt S Trout - E<lt>mst@shadowcat.co.ukE<gt> - original author
94caac6e 676
02f5a508 677Company: http://www.shadowcat.co.uk/
94caac6e 678Blog: http://chainsawblues.vox.com/
679
1795217c 680Florian Ragwitz E<lt>rafl@debian.orgE<gt> - maintainer
681
0df492b9 682osfameron E<lt>osfameron@cpan.orgE<gt> - first draft of documentation
dcf29eb6 683
107322d1 684=head1 COPYRIGHT AND LICENSE
685
09addf7a 686This library is free software under the same terms as perl itself
687
107322d1 688Copyright (c) 2007, 2008, 2009 Matt S Trout
689
690Copyright (c) 2008, 2009 Florian Ragwitz
94caac6e 691
09addf7a 692stolen_chunk_of_toke.c based on toke.c from the perl core, which is
693
694Copyright (C) 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
6952000, 2001, 2002, 2003, 2004, 2005, 2006, by Larry Wall and others
94caac6e 696
697=cut
698
6991;