While working on the Cat to MSIL compiler I ran into some very annoying security features.
The MSIL has some security features to try and prevent bad code from being executed. This has two problems: 1) it prevents language implementors from doing interesting things, 2) it can be circumvented. This reminds me of runnning up against a lot of the C++ features designed to prevent abuse.
The specific feature I am bellyaching about is the fact that a specific function can't manipulate the stack below its stack-frame, and can't manipulate the stack beyond its max-stack size. Furthermore a function can't create a non-deterministic (at compile-time) stack configuration with regards to the number and type of elements on the stack.
What this just means is that to translate from Cat to MSIL I have to emulate a more flexible stack. To try and leverage the efficiency of performing the MSIL byte-code operations, I am introducing a notion of a separate evaluation stack. In the old Cat model, everything occured on a single stack but in the next version the basic operations occur on an evaluation stack.
This however has lead to an interesting fact: all of the MSIL opcodes are going to be available directly from Cat. Apart from the usual operators, there is going to be two addtional operators: msil_load and msil_store. These operators copy to and from the main stack and the evaluation stack respectiviely. Now the entire set of MSIL operators will be exposed as follows: msil.Add, msil.Add_Ovf, msil.Add_Ovf_Un, ...
I don't know much assembly, but I'm going to learn it (don't expect quick results!). If I know enough, I'll write a compiler for a stack based language that's simpler than Cat, and maybe a Cat compiler after that. One thing that may be a problem is that [a b c] is a list of a b and c *and* it's a function (I don't know much Cat, but it's the same as Joy I assume). This could make the language less efficient and hard to compile.
If you have this:
a = [b] [c] ifel
you can compile it to something like this:
a = 'b 'c ifel
('b means: push the location of the 'b procedure on the stack)
a = [b c d] i
a = 'foo i foo = b c d
label a: // ... push('b) goto pop()
No promises, but I do find Cat very interesting (at the moment ;-)) & probably promising.