Suppose X is the input language, Z is the output language, then f is the compiler, which is written in language Y.
f = X -> Z
Since f is only a program, I think Y can be any language, right? So we can have compilers f1, f2, each written in Y1, Y2.
f1 = f Y1 f2 = f Y2 g = Z -> M h = g . f # We get a compiler X -> M
Take cpython compiler for example, X is Python, Z is the Python VM code, Y is C.
cpython = Python -> PythonVMCode C interpreter = PythonVMCode -> Nothing interpreter2 = PythonVMCode -> MachineCode
Python sources are compiled to the Python VM code, the .pyc files, then interpreted by the interpreter. Looks like it's possible there exists a compiler which can directly do Python -> MachineCode, though much hard to implement:
hardpython = interpreter2 . cpython
We can also write another compiler do the work Python -> PythonVMCode, in another language, say Python itself.
mypython = Python -> PythonVMCode Python mypython2 = Python -> PythonVMCode Ruby
Now, here is the complicated example PyPy. I'm just a newbie of PyPy, correct me if I'm wrong:
Our goal is to provide a possible solution to the problem of language implementers: having to write l * o * p interpreters for l dynamic languages and p platforms with o crucial design decisions.
We can think l is X, p is Y. There exists a program which translates all RPython programs to C:
rpython_compiler = RPython -> C Python pypy = Python -> Nothing RPython translate = compile the program pypy written in RPython using rpython_compiler py2rpy = Python -> RPython Python py2c = Python -> C Python py2c = rpython_compiler . py2rpy
RPython programs are just like VM instructions, rpython_compiler is the VM.
q1. pypy is the interpreter, a RPython program which can interpret Python code, there is no output language, so we can't consider it as a compiler, right?
- I just found that even if after the translating, pypy is still a interpreter, only this time written in C.
- If we look deep into the interpreter pypy, I believe there must exist some kind of compiler, which compiles the Python sources to some AST, then execute
compiler_inside_pypy = Python -> AST_or_so
q2. Can compiler py2rpy exist, transforming all Python programs to RPython? In which language it's written is irrelevant. If yes, we get another compiler py2c. What's the difference between pypy and py2rpy in nature? Is py2rpy much harder to write than pypy?
q3. Is there some general rules or theory available about this?
gcc_c = C -> asm? C # not sure, gimple or rtl? g++ = C++ -> asm? C clang = C -> LLVM_IR C++ jython = Python -> JVMCode java ironpython = Python -> CLI C#
q4. Given f = X -> Z, a program P written in X. When we want to speed up P, what can we do? Possbile ways:
rewrite P in more efficient algorithm
rewrite f to generate better Z
if Z is interpreted, write a better Z interpreter (PyPy is at here?)
speed up programs written in Z recursively
get a better machine
ps. This question is not about the tech stuffs of how to write a compiler, but the feasibility and complexity of write a certain kind compiler.