Search code examples
pythonrecursionmemory-managementlinux-kernelcpython

Kernel visibility into the call stack in Python


Does the OS have visibility into the call stack (e.g. calls made between functions) in CPython? E.g. In what way is the OS involved in the creation, retrieval and/or management of the Python stack and operations of its stack frames?

Context:

  • My understanding is that the Python interpreter does not support tail call recursion, so this seems to be something left to Python to handle.
  • Most OS impose a maximum limit on the size of a stack (e.g. I believe in Linux OS the maximum stack size is 8192 KB by default but it can be changed via e.g. ulimit), meaning the kernel clearly can get involved in at least limiting the size of the call stack.

Solution

  • In what way is the OS involved in the creation, retrieval and/or management of the Python stack and operations of its stack frames?

    It isn't. The stack frames are for the process to take care of, the kernel does not interfere.

    My understanding is that the Python interpreter does not support tail call recursion, so this seems to be something left to Python to handle.

    Well yes, it's Python's job to handle its own stack, regardless of tail recursion. The fact that Python does not support tail recursion may have some disadvantages for deep recursive calls, but the code could always be rewritten as iterative.

    See also: What is the maximum recursion depth in Python, and how to increase it?

    the kernel clearly can get involved in at least limiting the size of the call stack

    Yes, indeed the kernel does limit the stack size. The way it is done is by allocating an invisible guard page just after the top of the stack: when the stack is full, making another call (thus adding another stack frame) will trigger reads and/or writes into the guard page, and the kernel will detect it and increase the stack size. This only happens up to a certain predefined amount though, after which the process is killed for exceeding the maximum allowed stack size.

    See also: Stack memory management in Linux