Skip to content
This repository has been archived by the owner on Feb 3, 2021. It is now read-only.

Commit

Permalink
[nqp]: Add class declarations and method calls.
Browse files Browse the repository at this point in the history
  • Loading branch information
pmichaud committed Oct 28, 2009
1 parent 742167e commit e1d65a0
Show file tree
Hide file tree
Showing 3 changed files with 65 additions and 3 deletions.
36 changes: 35 additions & 1 deletion src/NQP/Actions.pm
Expand Up @@ -142,6 +142,24 @@ method variable($/) {
}

method package_declarator:sym<module>($/) { make $<package_def>.ast; }
method package_declarator:sym<class>($/) {
my $classinit :=
PAST::Op.new(
PAST::Op.new(
:inline( ' %r = get_root_global ["parrot"], "P6metaclass"')
),
~$<package_def><name>,
:name('new_class'),
:pasttype('callmethod')
);
if $<package_def><parent> {
$classinit.push( PAST::Val.new(
:value( ~$<package_def><parent>[0] ),
:named('parent') ) );
}
@BLOCK[0].loadinit.push($classinit);
make $<package_def>.ast;
}

method package_def($/) {
my $past := $<pblock> ?? $<pblock>.ast !! $<comp_unit>.ast;
Expand Down Expand Up @@ -187,6 +205,14 @@ method variable_declarator($/) {
}

method routine_declarator:sym<sub>($/) { make $<routine_def>.ast; }
method routine_declarator:sym<method>($/) {
my $past := $<routine_def>.ast;
if $past.isa(PAST::Var) { $past := $past.viviself(); }
$past.blocktype('method');
$past[0].unshift( PAST::Op.new( :inline(' .lex "self", self') ) );
$past.symbol('self', :scope('lexical') );
make $past;
}

method routine_def($/) {
my $past := $<blockoid>.ast;
Expand All @@ -195,7 +221,6 @@ method routine_def($/) {
if $<deflongname> {
my $name := ~$<deflongname>[0];
$past.name($name);
$past.nsentry('');
$past := PAST::Var.new( :name($name), :isdecl(1), :viviself($past),
:scope('lexical') );
$past<XXXroutine> := 1;
Expand Down Expand Up @@ -254,6 +279,13 @@ method named_param($/) {
make $past;
}

method dotty($/) {
my $past := $<args> ?? $<args>[0].ast !! PAST::Op.new( :node($/) );
$past.name( ~$<identifier> );
$past.pasttype('callmethod');
make $past;
}

method term:sym<identifier>($/) {
my $past := $<args>.ast;
$past.name(~$<identifier>);
Expand Down Expand Up @@ -360,6 +392,8 @@ method nulltermish($/) {
make $<noun> ?? $<noun>.ast !! 0;
}

method postfix:sym<.>($/) { make $<dotty>.ast; }

method postfix:sym<++>($/) {
make PAST::Op.new( :name('postfix:<++>'),
:inline(' clone %r, %0', ' inc %0'),
Expand Down
17 changes: 15 additions & 2 deletions src/NQP/Grammar.pm
Expand Up @@ -130,6 +130,7 @@ token twigil { <[*]> }

proto token package_declarator { <...> }
token package_declarator:sym<module> { <sym> <package_def> }
token package_declarator:sym<class> { <sym> <package_def> }

rule package_def {
<name>
Expand All @@ -153,7 +154,8 @@ rule scoped {
token variable_declarator { <variable> }

proto token routine_declarator { <...> }
token routine_declarator:sym<sub> { <sym> <routine_def> }
token routine_declarator:sym<sub> { <sym> <routine_def> }
token routine_declarator:sym<method> { <sym> <routine_def> }

rule routine_def {
<deflongname=ident>?
Expand Down Expand Up @@ -184,6 +186,15 @@ token named_param {

rule default_value { '=' <EXPR('i=')> }

token dotty {
'.' <identifier>
[
| <?[(]> <args>
| ':' \s <args=arglist>
]?
}


proto token term { <...> }

token term:sym<identifier> {
Expand All @@ -201,7 +212,7 @@ token args {
token arglist {
<.ws>
[
| <EXPR>
| <EXPR('f=')>
| <?>
]
}
Expand Down Expand Up @@ -248,6 +259,8 @@ token postcircumfix:sym<ang> {
<O('%methodop')>
}

token postfix:sym<.> { <dotty> <O('%methodop')> }

token prefix:sym<++> { <sym> <O('%autoincrement, :pirop<inc>')> }
token prefix:sym<--> { <sym> <O('%autoincrement, :pirop<dec>')> }
token postfix:sym<++> { <sym> <O('%autoincrement')> } # see Actions.pm
Expand Down
15 changes: 15 additions & 0 deletions t/nqp/25-class.t
@@ -0,0 +1,15 @@
#!./parrot nqp.pbc

# class

plan(1);

class XYZ {
method foo($x) {
say($x);
}
}

my $xyz := XYZ.new();

$xyz.foo('ok 1');

0 comments on commit e1d65a0

Please sign in to comment.