Earlier quoted context omitted.
I feel like using calling conventions to massage the compiler's register allocation strategy is a hack. If the problem is manual control over register allocation, then the ideal solution should be... well, exactly that and no more? An annotation for local variables indicating "always spill this" (for cold-path locals) or "never spill this or else trigger a build error" (for hot-path locals). Isn't that literally why…
If the tail calling pattern made the code ugly, I would be more inclined to agree with this. But putting each opcode in its own function isn't so bad: it seems just as readable, if not more so, than a mondo function that implements every opcode. By contrast, a mondo function that also has a bunch of register allocation annotations seems less readable.
A tail calling interpreter for Python (already landed in CPython)
91–93 of 93 posts
Re: A tail calling interpreter for Python (already landed in CPython)
#92Earlier quoted context omitted.
The JIT will improve - you can also use PyPy to get speedups on programs that don't use a ton of C extensions. Also, free-threading is coming so we'll have threads soon. I don't know if Python can every really be fast as by design, objects are scattered all over memoryand even things like iterating a list, you're chasing pointers to PyObject all over the place - it's just not cache friendly.
PyPy has a list implementation that specializes under the hood. So if you stuff it with integers, it will contain the integers directly instead of pointers to them. That's at least how I understood it.
Re: A tail calling interpreter for Python (already landed in CPython)
#93Earlier quoted context omitted.
If the tail calling pattern made the code ugly, I would be more inclined to agree with this. But putting each opcode in its own function isn't so bad: it seems just as readable, if not more so, than a mondo function that implements every opcode. By contrast, a mondo function that also has a bunch of register allocation annotations seems less readable.
I don't see how a hypothetical __attribute__((never_spill)) annotation on local variables would preclude splitting opcode logic into separate functions. It just means those functions would have to be inlined into the interpreter loop to avoid conflicts with calling convention constraints.