Author: jonathan
Date: Tue Nov 11 11:44:51 2008
New Revision: 32554
Modified:
trunk/languages/perl6/perl6.pir
trunk/languages/perl6/src/builtins/guts.pir
trunk/languages/perl6/src/parser/actions.pm
Log:
[rakudo] Some very basic support for MAIN entry point sub. Just passes all
command line arguments as positionals.
Modified: trunk/languages/perl6/perl6.pir
==============================================================================
--- trunk/languages/perl6/perl6.pir (original)
+++ trunk/languages/perl6/perl6.pir Tue Nov 11 11:44:51 2008
@@ -160,24 +160,21 @@
.sub 'main' :main
.param pmc args_str
- ## create @ARGS global. We could possibly use the args pmc
- ## coming directly from Parrot, but currently Parrot provides
- ## it as a ResizableStringArray and we need Undefs for
- ## non-existent elements (RSA gives empty strings).
- .local pmc args, iter
- args = new 'List'
- iter = new 'Iterator', args_str
- args_loop:
- unless iter goto args_end
- $P0 = shift iter
- push args, $P0
- goto args_loop
- args_end:
- set_hll_global '@ARGS', args
+ ## Set up @*ARGS.
+ .local pmc args
+ args = '!SETUP_ARGS'(args_str, 0)
$P0 = compreg 'Perl6'
$P1 = $P0.'command_line'(args, 'encoding'=>'utf8',
'transcode'=>'iso-8859-1')
+ ## Now execute any MAIN sub.
+ .local pmc main_sub, args
+ main_sub = get_hll_global 'MAIN'
+ if null main_sub goto no_main
+ args = get_hll_global '@ARGS'
+ main_sub(args :flat)
+ no_main:
+
.include 'iterator.pasm'
.local pmc iter
$P0 = get_hll_global ['Perl6'], '@?END_BLOCKS'
Modified: trunk/languages/perl6/src/builtins/guts.pir
==============================================================================
--- trunk/languages/perl6/src/builtins/guts.pir (original)
+++ trunk/languages/perl6/src/builtins/guts.pir Tue Nov 11 11:44:51 2008
@@ -251,6 +251,34 @@
.end
+=item !SETUP_ARGS
+
+Sets up the @*ARGS global. We could possibly use the args pmc coming directly
+from Parrot, but currently Parrot provides it as a ResizableStringArray and we
+need Undefs for non-existent elements (RSA gives empty strings).
+
+=cut
+
+.sub '!SETUP_ARGS'
+ .param pmc args_str
+ .param int strip_program_name
+ .local pmc args, iter
+ args = new 'List'
+ iter = new 'Iterator', args_str
+ args_loop:
+ unless iter goto args_end
+ $P0 = shift iter
+ push args, $P0
+ goto args_loop
+ args_end:
+ unless strip_program_name goto done
+ $P0 = shift args
+ done:
+ set_hll_global '@ARGS', args
+ .return (args)
+.end
+
+
=item !keyword_class(name)
Internal helper method to create a class.
Modified: trunk/languages/perl6/src/parser/actions.pm
==============================================================================
--- trunk/languages/perl6/src/parser/actions.pm (original)
+++ trunk/languages/perl6/src/parser/actions.pm Tue Nov 11 11:44:51 2008
@@ -56,6 +56,64 @@
)
);
+ # emit a :main block that acts as the entry point in pre-compiled scripts
+ $past.push(
+ PAST::Block.new(
+ :pirflags(':main'),
+ PAST::Op.new(
+ :pasttype('call'),
+ :name('!SETUP_ARGS'),
+ PAST::Var.new(
+ :name('args_str'),
+ :scope('parameter')
+ ),
+ PAST::Val.new( :value(1) )
+ ),
+ PAST::Op.new(
+ :inline(
+ '$P0 = interpinfo .INTERPINFO_CURRENT_SUB',
+ '$P0 = $P0."get_outer"()',
+ '$P0()'
+ )
+ ),
+ PAST::Op.new(
+ :pasttype('bind'),
+ PAST::Var.new(
+ :name('main_sub'),
+ :scope('register'),
+ :isdecl(1)
+ ),
+ PAST::Var.new(
+ :name('MAIN'),
+ :scope('package')
+ )
+ ),
+ PAST::Op.new(
+ :pasttype('unless'),
+ PAST::Op.new(
+ :pirop('isnull'),
+ PAST::Var.new(
+ :name('main_sub'),
+ :scope('register')
+ )
+ ),
+ PAST::Op.new(
+ :pasttype('call'),
+ PAST::Var.new(
+ :name('main_sub'),
+ :scope('register')
+ ),
+ PAST::Var.new(
+ :name('@ARGS'),
+ :scope('package'),
+ :namespace(''),
+ :flat(1)
+ )
+ )
+ )
+ )
+ );
+
make $past;
}