diff options
| author | Drahflow <drahflow@gmx.de> | 2013-01-14 12:53:09 +0100 |
|---|---|---|
| committer | Drahflow <drahflow@gmx.de> | 2013-01-14 12:53:09 +0100 |
| commit | fe0d09cfceff89d3215f3fa3f148ac3130d9b91a (patch) | |
| tree | bdb8b4f74ee17bf862cbc5045c9e8fb450b5ed16 /interpreter | |
| parent | 347a635d04df610e1a5a56a46eddf071533a13ac (diff) | |
I heard you like JIT, so I put some JIT in your JIT
Diffstat (limited to 'interpreter')
| -rw-r--r-- | interpreter/Elymas.pm | 36 | ||||
| -rw-r--r-- | interpreter/ElymasGlobal.pm | 57 |
2 files changed, 78 insertions, 15 deletions
diff --git a/interpreter/Elymas.pm b/interpreter/Elymas.pm index 20f8c36..eb514fa 100644 --- a/interpreter/Elymas.pm +++ b/interpreter/Elymas.pm @@ -7,7 +7,7 @@ require Exporter; our @ISA = qw(Exporter); our @EXPORT = qw( popInt popString popArray arrayAccess $quoted @globalCallStack - interpretCode execute executeString executeFile resolve canCastTo typeEqual + interpretCode compileCode execute executeString executeFile resolve canCastTo typeEqual ); use Data::Dumper; @@ -73,6 +73,40 @@ sub interpretCode { } } +sub compileCode { + my ($code) = @_; + + my $ret = "my \$i = 0; eval {\n"; + + foreach my $i (0 .. $#$code) { + my $t = $code->[$i]; + + if(ref($t->[1]) eq 'ARRAY' and $t->[1]->[0] eq 'func') { + if(not $t->[1]->[2]) { + # untyped function, just call, no need to go through execute + $ret .= "push \@globalCallStack, \$code[$i];\n"; + $ret .= "&{\$code[$i]->[0]}(\$data, \$lscope);\n"; + $ret .= "pop \@globalCallStack;\n"; + } else { + $ret .= "\$i = $i; execute(\$code[$i], \$data, \$lscope);\n"; + } + } else { + $ret .= "push \@\$data, \$code[$i];\n"; + } + } + + $ret .= <<'EOPERL'; + }; + if($@) { + print "Stack: " . Dumper($data); + print "Token: " . Dumper($code[$i]); + die; + } +EOPERL + + return $ret; +} + sub typeStack { my ($type) = @_; diff --git a/interpreter/ElymasGlobal.pm b/interpreter/ElymasGlobal.pm index 5384cb5..a93760d 100644 --- a/interpreter/ElymasGlobal.pm +++ b/interpreter/ElymasGlobal.pm @@ -51,23 +51,52 @@ our $global = { die "unexpanded token in quoted code" if grep { $_->[1] eq 'tok' } @code; - if($quoted) { - push @$data, [sub { - my ($data, $refScope) = @_; - my $scope = $$refScope; + # if($quoted) { + # push @$data, [sub { + # my ($data, $refScope) = @_; + # my $scope = $$refScope; + + # push @$data, [sub { + # my ($data) = @_; + # my $lscope = \{ ' parent' => $scope }; + # interpretCode(\@code, $data, $lscope); + # }, ['func', 'Dumper(\@code)']]; + # }, ['func', 'func-quoted'], \@code]; + # } else { + # push @$data, [sub { + # my ($data) = @_; + # my $lscope = \{ ' parent' => $scope }; + # interpretCode(\@code, $data, $lscope); + # }, ['func', 'Dumper(\@code)']]; + # } - push @$data, [sub { + if($quoted) { + my $sub = <<'EOPERL' . + sub { + my ($data, $refScope) = @_; + my $scope = $$refScope; + my $s = sub { + my ($data) = @_; + my $lscope = \{ ' parent' => $scope }; +EOPERL + compileCode(\@code) . <<'EOPERL'; + }; + push @$data, [$s, ['func', 'compiled sub (1)']]; + } +EOPERL + $sub = eval($sub); + push @$data, [$sub, ['func', 'func-quoted'], \@code]; + } else { + my $sub = <<'EOPERL' . + sub { my ($data) = @_; my $lscope = \{ ' parent' => $scope }; - interpretCode(\@code, $data, $lscope); - }, ['func', 'Dumper(\@code)']]; - }, ['func', 'func-quoted'], \@code]; - } else { - push @$data, [sub { - my ($data) = @_; - my $lscope = \{ ' parent' => $scope }; - interpretCode(\@code, $data, $lscope); - }, ['func', 'Dumper(\@code)']]; +EOPERL + compileCode(\@code) . <<'EOPERL'; + }; +EOPERL + $sub = eval($sub); + push @$data, [$sub, ['func', 'compiled sub (2)']]; } }, ['func', '}'], 'quote'], "}'" => [sub { |
