Author: jonathan
Date: Mon Feb 25 15:55:00 2008
New Revision: 26062

Modified:
   trunk/languages/perl6/src/parser/actions.pm

Log:
[rakudo] Make $.x used away from declaration with has do something closer to 
the right thing.

Modified: trunk/languages/perl6/src/parser/actions.pm
==============================================================================
--- trunk/languages/perl6/src/parser/actions.pm (original)
+++ trunk/languages/perl6/src/parser/actions.pm Mon Feb 25 15:55:00 2008
@@ -779,13 +779,14 @@
     my $name := $past.name();
     our $?BLOCK;
     unless $?BLOCK.symbol($name) {
-        $past.isdecl(1);
         my $scope := 'lexical';
         my $declarator := $<declarator>;
         if $declarator eq 'my' {
+            $past.isdecl(1);
         }
         elsif $declarator eq 'our' {
             $scope := 'package';
+            $past.isdecl(1);
         }
         elsif $declarator eq 'has' {
             # Set that it's attribute scope.
@@ -888,11 +889,6 @@
         ));
     }
     else {
-        # Set how it vivifies.
-        my $viviself := 'Undef';
-        if $<sigil> eq '@' { $viviself := 'List'; }
-        if $<sigil> eq '%' { $viviself := 'Hash'; }
-
         # Handle naming.
         my @ident := $<name><ident>;
         my $name;
@@ -902,36 +898,54 @@
         PIR q<  $P1 = pop $P0            >;
         PIR q<  store_lex '$name', $P1   >;
 
-        # ! twigil should be kept in the name.
-        if $<twigil>[0] eq '!' { $name := '!' ~ ~$name; }
+        # If it's $.x, it's a method call, not a variable.
+        if $<twigil>[0] eq '.' {
+            $past := PAST::Op.new(
+                :node($/),
+                :pasttype('callmethod'),
+                :name($name),
+                PAST::Op.new(
+                    :inline('%r = self')
+                )
+            );
+        }
+        else {
+            # Variable. Set how it vivifies.
+            my $viviself := 'Undef';
+            if $<sigil> eq '@' { $viviself := 'List'; }
+            if $<sigil> eq '%' { $viviself := 'Hash'; }
+
+            # ! twigil should be kept in the name.
+            if $<twigil>[0] eq '!' { $name := '!' ~ ~$name; }
+
+            # All but subs should keep their sigils.
+            my $sigil := '';
+            if $<sigil> ne '&' {
+                $sigil := ~$<sigil>;
+            }
 
-        # All but subs should keep their sigils.
-        my $sigil := '';
-        if $<sigil> ne '&' {
-            $sigil := ~$<sigil>;
-        }
-
-        # If we have no twigil, but we see the name noted as an attribute in
-        # an enclosing scope, add the ! twigil anyway; it's an alias.
-        if $<twigil>[0] eq '' {
-            our @?BLOCK;
-            for @?BLOCK {
-                if defined( $_ ) {
-                    my $sym_table := $_.symbol($sigil ~ $name);
-                    if defined( $sym_table ) && $sym_table<scope> eq 
'attribute' {
-                        $name := '!' ~ $name;
+            # If we have no twigil, but we see the name noted as an attribute 
in
+            # an enclosing scope, add the ! twigil anyway; it's an alias.
+            if $<twigil>[0] eq '' {
+                our @?BLOCK;
+                for @?BLOCK {
+                    if defined( $_ ) {
+                        my $sym_table := $_.symbol($sigil ~ $name);
+                        if defined( $sym_table ) && $sym_table<scope> eq 
'attribute' {
+                            $name := '!' ~ $name;
+                        }
                     }
                 }
             }
-        }
-
-        $past := PAST::Var.new( :name( $sigil ~ $name ),
-                                :viviself($viviself),
-                                :node($/)
-                              );
-        if @ident || $<twigil>[0] eq '*' {
-            $past.namespace(@ident);
-            $past.scope('package');
+        
+            $past := PAST::Var.new( :name( $sigil ~ $name ),
+                                    :viviself($viviself),
+                                    :node($/)
+                                  );
+            if @ident || $<twigil>[0] eq '*' {
+                $past.namespace(@ident);
+                $past.scope('package');
+            }
         }
     }
     make $past;

Reply via email to