You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Recursively calling makepasv() finally leads to core dumped. #90369
See the following 'test.py', we call client.makepasv() in socket, and then create_connection. Recursively calling makepasv() finally leads to core dumped.
System: Python 3.10.1, 3.11.0a3 ,master on Ubuntu 18.04
Reproduce step:
executing "python test.py"
If only TimeoutError is observed, just executing this code again. Maybe after 4 or 5 times, this program crashes Python interpreter.
Exception in thread Thread-1:
Traceback (most recent call last):
File "/home/xxm/Desktop/compilers/cpython-main12-31/Lib/asyncore.py", line 90, in read
obj.handle_read_event()
^^^^^^^^^^^^^^^^^^^^^^^
File "/home/xxm/Desktop/compilers/cpython-main12-31/Lib/asyncore.py", line 427, in handle_read_event
Traceback (most recent call last):
.....
File "/home/xxm/Desktop/compilers/cpython-main12-31/Lib/test/test_ftplib.py", line 298, in runreturnself._sock.recv_into(b)
^^^^^^^^^^^^^^^^^^^^^^^TimeoutError: timed out
Fatal Python error: _enter_buffered_busy: could not acquire lock for <_io.BufferedWriter name='<stderr>'> at interpreter shutdown, possibly due to daemon threads
Python runtime state: finalizing (tstate=0x0000556df3cfbe30)
Current thread 0x00007fb82ce69080 (most recent call first):
<no Python frame>
The reproduction no longer works on current HEAD. However, it is recursively opening FTP connections until it either runs out of FDs or the stack overflows. The crash is coming from a daemon thread started by the test code, which is inherently racy with shutdown.
Since test framework is only meant for internal use and it isn't being used correctly, I'd normally suggest just closing this. However, IIUC, we do want to eliminate daemon threads and their raciness where we can (right @ZeroIntensity?).
As it turns out the threads were originally joinable and were daemonized in 529525f for #7079, but the code that joined them was left intact. The commit message doesn't mention the change and it looks like it was perhaps a mistake. @tiran, do you recall anything about it?
There was another thread in test_poplib which was daemonized in the same commit and which can also be made joinable safely.
However, IIUC, we do want to eliminate daemon threads and their raciness where we can (right @ZeroIntensity?).
I personally don't like daemon threads, but they're not necessarily an issue themself. See this section in PEP 788. Ideally, we'll solve the raciness in C code via interpreter references, not by removing usage of daemon threads from Python code.
Activity
xxm commentedon Dec 31, 2021
See the following 'test.py', we call client.makepasv() in socket, and then create_connection. Recursively calling makepasv() finally leads to core dumped.
System: Python 3.10.1, 3.11.0a3 ,master on Ubuntu 18.04
Reproduce step:
test.py
===============================================
===============================================
Error Message:
---------------------------------------------------
Current thread 0x00007fb82ce69080 (most recent call first):
<no Python frame>
Extension modules: _testcapi (total: 1)
Aborted (core dumped)
-----------------------------------------------------
duaneg commentedon Jun 16, 2025
The reproduction no longer works on current
HEAD. However, it is recursively opening FTP connections until it either runs out of FDs or the stack overflows. The crash is coming from a daemon thread started by the test code, which is inherently racy with shutdown.Since test framework is only meant for internal use and it isn't being used correctly, I'd normally suggest just closing this. However, IIUC, we do want to eliminate daemon threads and their raciness where we can (right @ZeroIntensity?).
As it turns out the threads were originally joinable and were daemonized in 529525f for #7079, but the code that
joined them was left intact. The commit message doesn't mention the change and it looks like it was perhaps a mistake. @tiran, do you recall anything about it?There was another thread in
test_poplibwhich was daemonized in the same commit and which can also be made joinable safely.pythongh-90369: change test server threads to joinable
ZeroIntensity commentedon Jun 16, 2025
I personally don't like daemon threads, but they're not necessarily an issue themself. See this section in PEP 788. Ideally, we'll solve the raciness in C code via interpreter references, not by removing usage of daemon threads from Python code.
ZeroIntensity commentedon Jun 23, 2025
Closing per discussion in GH-135560