Open PalumboN opened 9 months ago
Just to document it, here it is.
The interpreter is made so all functions/methods are inlined by default by slang if possible. This way, there are as few exit points from the interpreter function as possible. However, this can create code explosion for long methods that are shared by many bytecodes. This is for example the case for the send bytecodes that all call the long routine to lookup + activate.
To avoid this, instead of inlining long methods into the interpreter loop, some of these code paths are inlined once and shared by all the users using a goto
.
The pragma sharedCodeInCase:
controls this. It tells that the function should be inlined only once in the context of the bytecode given as parameter of the pragma. Then, Slang will translate all calls to this function to a goto
if they are not the owner of the shared case.
Now, the point is that since this sharedCodeInCase:
is implemented through goto
s, this means that control jumps to the shared code but it's not easy to make it come back.
This means that this only works when the shared code is the tail of the bytecode: we don't need its return value, and we don't need control to come back. That's why shared code cases will in general be responsible for fetching the next instruction or doing the corresponding stack manipulation (pushes/pops).
-- EDIT--
also just FTR, why this is an issue in https://github.com/pharo-project/pharo-vm/pull/743#discussion_r1486157265
The thing is that to be able to translate booleanCheatTrueSistaV1
et al correctly in Druid, we need to have a single pop instruction and not two (one at the end of each tail. The refactored code does that by extracting the pop to the caller, and using the return value of the offending function. But this breaks the premise of the sharedCodeInCase:
.
But with my changes such a translation is not valid anymore. We should probably discuss this better.
_Originally posted by @guillep in https://github.com/pharo-project/pharo-vm/pull/743#discussion_r1486157265_