|
Perl 6
SMOP s1p Language: Revision 10
Considering SMOP doesn't use the C stack for regular operation, we have an important side effect that not even the built-in types can recurse in the C stack. They must recurse only using the SMOP interpreter, and only do C recursion when really needed. This way, it sounds a little awkward to write C code that doesn't run like normal C code. It would tend to be worse than XS. That's why we need a Stage 1 language. This language would result in the equivalent C code to declare the type.
This code, by one side, is just plain Perl 6, because the object support is the same as Perl 6, but, as a Stage 1 there are some limitations of what code can be generated, remembering that this Stage 1 code must be subject to translation into C code. Basically, this language will be used to build a interpreter operations. And to do that, it doesn't need: * lexical scope - This language will have to use the interpreter functions to manipulate the language variables. This means that lexical variables can only exist inside a method, and that there are no global variables. * dynamic name resolution - All the names in the language must be known barewords for both method names and for type names. For method names the SMOP Constant Identifiers should be used, and for the types, the compiler should know the ones defined by smop_builtin.h and smop_native.h. This basically means that all lexical information will be translated to anonymous stack referencing, as block names, and they will only be accessible from the current file. On the other hand, the language will be used, at the same time, to describe the built-in types and implement them in high level. In order to allow this description, while recognizing the limitations, so here we get to a more precise description. The stage 1 language will describe Classes that happens to be built-in classes, so the basic syntax will be the same as of a regular Perl 6 class, the methods will be understood as the class methods, subroutines are not allowed. ^ _Warning: The Following code dosn't work_ ^^ Small exercise .pre class Foo { has $.a; has $!b; method foo { return self.bar } method bar { return 1 } } .pre Should be translated into .pre #include <smop.h> #include <smop_lowlevel.h> #include <smop_oo.h> .pre ^^ Method body .pre method fib(int $n) { if ($n == 0) { 0 } elsif ($n == 1) { 1 } else { fib($n - 1) + fib($n - 2) } } .pre Could be compiled to the following sm0p code. .pre SMOP__Object* SMOP__S1P__method_fib; void SMOP__S1P__method_fib_boot() { SMOP__Object* SMOP__ID__fib = SMOP__NATIVE__idconst_create("fib"); fib = SMOP__OO__LOWL__Method_create(0, SMOP__ID__fib, SMOP__NATIVE__bool_false, SMOP__S1P__method_fib_run); }; void SMOP__S1P__method_fib_run(SMOP__Object* interpreter, SMOP__Object* method, SMOP__Object* capture) { SMOP__Object* n = SMOP__NATIVE__capture_positional(interpreter,capture,0); SMOP__Object* then1,else1,then2,else2,frame; then1 = q:sm0p { 0; }; then2 = q:sm0p { 1; }; else2 = q:sm0p { $n; SMOP__SLIME__CurrentFrame.copy(1); 1; 2; SMOP__SLIME__CurrentFrame.capturize(0,(4,2),(),2); SMOP__SLIME__CurrentFrame.capturize(0,(4,2),(),2); SMOP__OP__minus.call(); SMOP__OP__minus.call(); SMOP__SLIME__CurrentFrame.capturize(0,(2),(),2); SMOP__SLIME__CurrentFrame.capturize(0,(2),(),2); SMOP__S1P__method_fib.call(); SMOP__S1P__method_fib.call(); SMOP__SLIME__CurrentFrame.capturize(0,(1,2),(),1); SMOP__OP__plus.call(); }; else1 = q:sm0p { $n; 1; SMOP__SLIME__CurrentFrame.capturize(0,(1,2),(),2); "cond"; SMOP__OP__numeq.call(); "then"; $then2; "else"; $else2; SMOP__SLIME__CurrentFrame.capturize(0,(),(6,5,4,3,2,1),1); SMOP__OP__if.call(); }; SMOP__Object* current = SMOP_DISPATCH(interpreter,interpreter,SMOP__ID__continuation); frame = q:sm0p { $n; 0; SMOP__SLIME__CurrentFrame.capturize(0,(1,2),(),2); "cond"; SMOP__OP__numeq.call(); "then"; $then1; "else"; $else1; SMOP__SLIME__CurrentFrame.capturize(0,(),(6,5,4,3,2,1),1); SMOP__OP__if.call(); SMOP__SLIME__CurrentFrame.capturize(0,(1),(),1); $current.setr() interpreter.goto(|$current); }; SMOP_DISPATCH(interpreter, interpreter, SMOP__ID__goto, frame); }; .pre |