|Q: Intermediate code for interpreting & compiling? firstname.lastname@example.org (1995-02-10)|
|Re: Q: Intermediate code for interpreting & compiling? email@example.com (1995-02-14)|
|Re: Q: Intermediate code for interpreting & compiling? firstname.lastname@example.org (Charles Fiterman) (1995-02-14)|
|Re: Q: Intermediate code for interpreting & compiling? email@example.com (1995-02-22)|
|Re: Q: Intermediate code for interpreting & compiling? Dave@occl-cam.demon.co.uk (Dave Lloyd) (1995-02-24)|
|Re: Q: Intermediate code for interpreting & compiling? firstname.lastname@example.org (1995-02-24)|
|Re: Q: Intermediate code for interpreting & compiling? davidm@Rational.COM (1995-02-28)|
|Re: Q: Intermediate code for interpreting & compiling? email@example.com (1995-03-01)|
|From:||firstname.lastname@example.org (Torben AEgidius Mogensen)|
|Organization:||Department of Computer Science, U of Copenhagen|
|Date:||Tue, 14 Feb 1995 11:03:45 GMT|
email@example.com (Ryan Davis) writes:
>I am looking for some type of solution to a problem that I think arises
>enough. I am programming a language that will act much like smalltalk,
>namely, that it will be incrementally compiled into some form of
>intermediate code that will later be compiled OR interpreted. I would like
>it to be as generic (i.e. platform independant) as possible as I only
>really want to write it once and recompile on multiple machines with as
>little tweaking as possible... C is not a valid intermediate because then
>I would be implementing 2 languages at once and I'm not up to that yet...
>(Student, ya know...) that, and I think it would be easier to bring it to
>a lower level than that...
I suggest some form of stack-based intermediate language. It is very
easy to compile to this language, and it is very easy to interpret
too. Compilation to real machine code is not very hard either, unless
you are very concerned about efficiency.
A possible form for the stack code can contain the following
instructions (plus whatever else you need):
add: pop the two top elements off the stack, add them and
push the result back on. Similarly for other
const N: push the value N on top of the stack.
push N: take the value that is N places down the stack (the
top counts as 0) and push that on top of the stack.
update N: store the top stack value in position N down the
stack, then pop it off.
pop N: pop the N top values off the stack.
swap: swap the two topmost values on the stack.
goto N: jump to address N.
gosub N: push the address of the next instruction on the stack,
then jump to address N.
return: jump to the address at the top of the stack.
if= N: pop the two top values off the stack, compare them and
jump to N if they are equal. Similarly for other
comparison operators (if< etc.).
load: use the top value on the stack as an address to load a
value from memory, then replace the address with the
value (which becomes the new stack top).
store: use the top value on the stack as an address to store
the 2nd value on the stack in memory. Pop both off the
With these, it is trivial to compile airthmetic operations and various
loop and control structures. At a function call, the arguments are
pushed on the stack, the a gosub is done. The called function uses
push N instructions to access parameters (and local variables). At
return, the returned value is stored in the stack in the position of
the first argument (if there are no arguments, a dummy argument should
be pushed by the caller), the local variables are popped off (by pop
N) and a return is done. The calling procedure will then use pop N
again to remove the arguments (except the one that now contains the
result). The load and store operations can be used to implement
arrays. Add instructions for reading and printing etc. as necessary.
Torben Mogensen (firstname.lastname@example.org)
Return to the
Search the comp.compilers archives again.