1 package PPI::Token::Magic;
7 PPI::Token::Magic - Tokens representing magic variables
12 isa PPI::Token::Symbol
18 # When we say magic variables, we mean these...
19 $1 $2 $3 $4 $5 $6 $7 $8 $9
20 $_ $& $` $' $+ @+ %+ $* $. $/ $|
21 $\\ $" $; $% $= $- @- %- $) $#
22 $~ $^ $: $? $! %! $@ $$ $< $>
23 $( $0 $[ $] @_ @* $} $, $#+ $#-
24 $^L $^A $^E $^C $^D $^F $^H
25 $^I $^M $^N $^O $^P $^R $^S
30 C<PPI::Token::Magic> is a sub-class of L<PPI::Token::Symbol> which
31 identifies the token as "magic variable", one of the strange and
32 unusual variables that are connected to "things" behind the scenes.
34 Some are extremely common, like C<$_>, and others you will quite
35 probably never encounter in your Perl career.
39 The class provides no additional methods, beyond those provided by it's
40 L<PPI::Token::Symbol>, L<PPI::Token> and L<PPI::Element>.
45 use PPI::Token::Symbol ();
47 use vars qw{$VERSION @ISA %magic};
50 @ISA = 'PPI::Token::Symbol';
52 # Magic variables taken from perlvar.
53 # Several things added separately to avoid warnings.
55 $1 $2 $3 $4 $5 $6 $7 $8 $9
56 $_ $& $` $' $+ @+ %+ $* $. $/ $|
57 $\\ $" $; $% $= $- @- %- $)
58 $~ $^ $: $? $! %! $@ $$ $< $>
61 $^L $^A $^E $^C $^D $^F $^H
62 $^I $^M $^N $^O $^P $^R $^S
66 }, '$}', '$,', '$#', '$#+', '$#-' ) {
71 sub __TOKENIZER__on_char {
74 # $c is the candidate new content
75 my $c = $t->{token}->{content} . substr( $t->{line}, $t->{line_cursor}, 1 );
77 # Do a quick first test so we don't have to do more than this one.
78 # All of the tests below match this one, so it should provide a
79 # small speed up. This regex should be updated to match the inside
80 # tests if they are changed.
81 if ( $c =~ /^ \$ .* [ \w : \$ \{ ] $/x ) {
83 if ( $c =~ /^(\$(?:\_[\w:]|::))/ or $c =~ /^\$\'[\w]/ ) {
84 # If and only if we have $'\d, it is not a
85 # symbol. (this was apparently a concious choice)
86 # Note that $::0 on the other hand is legal
87 if ( $c =~ /^\$\'\d$/ ) {
88 # In this case, we have a magic plus a digit.
89 # Save the CURRENT token, and rerun the on_char
90 return $t->_finalize_token->__TOKENIZER__on_char( $t );
93 # A symbol in the style $_foo or $::foo or $'foo.
94 # Overwrite the current token
95 $t->{class} = $t->{token}->set_class('Symbol');
96 return PPI::Token::Symbol->__TOKENIZER__on_char( $t );
99 if ( $c =~ /^\$\$\w/ ) {
100 # This is really a scalar dereference. ( $$foo )
101 # Add the current token as the cast...
102 $t->{token} = PPI::Token::Cast->new( '$' );
105 # ... and create a new token for the symbol
106 return $t->_new_token( 'Symbol', '$' );
109 if ( $c eq '$#$' or $c eq '$#{' ) {
110 # This is really an index dereferencing cast, although
111 # it has the same two chars as the magic variable $#.
112 $t->{class} = $t->{token}->set_class('Cast');
113 return $t->_finalize_token->__TOKENIZER__on_char( $t );
116 if ( $c =~ /^(\$\#)\w/ ) {
117 # This is really an array index thingy ( $#array )
118 $t->{token} = PPI::Token::ArrayIndex->new( "$1" );
119 return PPI::Token::ArrayIndex->__TOKENIZER__on_char( $t );
122 if ( $c =~ /^\$\^\w+$/o ) {
123 # It's an escaped char magic... maybe ( like $^M )
124 my $next = substr( $t->{line}, $t->{line_cursor}+1, 1 ); # Peek ahead
125 if ($magic{$c} && (!$next || $next !~ /\w/)) {
126 $t->{token}->{content} = $c;
129 # Maybe it's a long magic variable like $^WIDE_SYSTEM_CALLS
134 if ( $c =~ /^\$\#\{/ ) {
135 # The $# is actually a case, and { is its block
136 # Add the current token as the cast...
137 $t->{token} = PPI::Token::Cast->new( '$#' );
140 # ... and create a new token for the block
141 return $t->_new_token( 'Structure', '{' );
143 } elsif ($c =~ /^%\^/) {
144 return 1 if $c eq '%^';
145 # It's an escaped char magic... maybe ( like %^H )
147 $t->{token}->{content} = $c;
150 # Back off, treat '%' as an operator
151 chop $t->{token}->{content};
152 bless $t->{token}, $t->{class} = 'PPI::Token::Operator';
157 # End the current magic token, and recheck
158 $t->_finalize_token->__TOKENIZER__on_char( $t );
161 # Our version of canonical is plain simple
162 sub canonical { $_[0]->content }
170 See the L<support section|PPI/SUPPORT> in the main module.
174 Adam Kennedy E<lt>adamk@cpan.orgE<gt>
178 Copyright 2001 - 2009 Adam Kennedy.
180 This program is free software; you can redistribute
181 it and/or modify it under the same terms as Perl itself.
183 The full text of the license can be found in the
184 LICENSE file included with this module.