
Hi, I use pypy to run an application in gunicorn. Gunicorn (as well) has a "preload" capability in multiprocess workers, which means it loads the application in one interpreter/process and instead of starting new interpreters/processes for additional workers, it just forks from the first one. This means the OS can share memory pages between the processes, which makes the app use less memory and start faster. This works nicely with pypy too and the memory savings are significant (taking into account that pypy uses much more memory than cpython, this is even more true). The problem is that each pypy process before the fork is "cold" and the JIT starts to compile code in the forked processes, independently from the original process, which makes a good deal of additonal memory (and CPU) go wasted. It would be nice to make this happen in the original process, so the operating system's COW semantics could work for the JIT-ed code too. Is there a way to achieve this? Thanks,

Seems you need to just trigger whatever heuristic causes the JIT to run on the interesting codepaths during application startup. Would having a small for loop in a module global namespace that called down through your stack do the trick? ===== somemodule.py def foo(...): # maybe this function calls through several layers of code in other # modules... ... for i in range(20): foo(...) # prewarm foo... ===== m On Sun, Mar 18, 2018 at 11:59:21AM +0100, Nagy, Attila wrote:
-- Matt Billenstein matt@vazor.com http://www.vazor.com/

Yeah, not very clean, but you could run dummy queries there that just exercised the hot code paths. It would be interesting to see if it worked though -- have a function that runs much faster after jit, warm it like this, then see if behaves the same after gunicorn forks the worker process. m On Wed, Mar 21, 2018 at 09:06:20AM +0100, Nagy, Attila wrote:
-- Matt Billenstein matt@vazor.com http://www.vazor.com/

Seems you need to just trigger whatever heuristic causes the JIT to run on the interesting codepaths during application startup. Would having a small for loop in a module global namespace that called down through your stack do the trick? ===== somemodule.py def foo(...): # maybe this function calls through several layers of code in other # modules... ... for i in range(20): foo(...) # prewarm foo... ===== m On Sun, Mar 18, 2018 at 11:59:21AM +0100, Nagy, Attila wrote:
-- Matt Billenstein matt@vazor.com http://www.vazor.com/

Yeah, not very clean, but you could run dummy queries there that just exercised the hot code paths. It would be interesting to see if it worked though -- have a function that runs much faster after jit, warm it like this, then see if behaves the same after gunicorn forks the worker process. m On Wed, Mar 21, 2018 at 09:06:20AM +0100, Nagy, Attila wrote:
-- Matt Billenstein matt@vazor.com http://www.vazor.com/
participants (2)
-
Matt Billenstein
-
Nagy, Attila