This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: ftplib does not honour "timeout" parameter for active data connections
Type: behavior Stage: resolved
Components: Library (Lib) Versions: Python 3.1, Python 3.2, Python 2.7, Python 2.6
process
Status: closed Resolution: fixed
Dependencies: Superseder:
Assigned To: giampaolo.rodola Nosy List: giampaolo.rodola, pitrou, r.david.murray, vstinner
Priority: normal Keywords: patch

Created on 2009-01-03 00:52 by giampaolo.rodola, last changed 2022-04-11 14:56 by admin. This issue is now closed.

Files
File name Uploaded Description Edit
ftplib.patch giampaolo.rodola, 2009-01-08 01:53 Modified patch which invokes settimeout() *before* accept()
Messages (6)
msg78912 - (view) Author: Giampaolo Rodola' (giampaolo.rodola) * (Python committer) Date: 2009-01-03 00:52
When using the optional ftplib.FTP()'s timeout parameter which 
specifies a timeout in seconds for blocking operations like the 
connection attempt, it is applied on both FTP control and passive data 
channel (if any).
It is not applied for active (PORT/EPRT) data connections.
The patch in attachment modifies ftplib so that when ntransfer method 
is called in active mode, timeout is applied on the resulting data 
connection.
msg79390 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2009-01-08 01:10
Your patch looks correct.
msg79392 - (view) Author: Giampaolo Rodola' (giampaolo.rodola) * (Python committer) Date: 2009-01-08 01:53
I'm sorry, I realized right now that settimeout() should be used also
*before* invoking accept(), to avoid the client to stall in case the
server does not establish any connection.
The second patch in attachment does that by using settimeout() straight
into FTP.makeport() method.
msg97061 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2009-12-30 21:33
This looks good, of course. Perhaps you want to add a test, if it isn't
too difficult to do so.
msg97095 - (view) Author: Giampaolo Rodola' (giampaolo.rodola) * (Python committer) Date: 2009-12-31 14:25
This time it's not easy as I see no way to distinguish whether the 
timeout exception gets raised by the command or the control socket, as 
makeport() method implementation deals with both:

<snippet>
        host = self.sock.getsockname()[0] 
        if self.af == socket.AF_INET:
            resp = self.sendport(host, port)  # socket.timeout can be 
raised here
        else:
            resp = self.sendeprt(host, port)   # ...here
        if self.timeout is not _GLOBAL_DEFAULT_TIMEOUT:
            sock.settimeout(self.timeout)    # or here
</snippet>

I think the best we can do is add a test which checks the timeout 
applied to the data socket resulting from a PASV/PORT request.
That doesn't cover this specific bug at all but it's something which is 
currently missing and that it would be nice to have.
msg103650 - (view) Author: Giampaolo Rodola' (giampaolo.rodola) * (Python committer) Date: 2010-04-19 22:30
Fixed as r80226 (2.7) and r80228 (3.2).
History
Date User Action Args
2022-04-11 14:56:43adminsetgithub: 49064
2010-04-19 22:30:45giampaolo.rodolasetstatus: open -> closed
priority: normal

components: + Library (Lib)
type: behavior
nosy: pitrou, vstinner, giampaolo.rodola, r.david.murray
messages: + msg103650
resolution: fixed
stage: resolved
2010-04-17 19:11:47giampaolo.rodolasetassignee: giampaolo.rodola

nosy: + r.david.murray
2009-12-31 14:25:39giampaolo.rodolasetmessages: + msg97095
2009-12-30 21:33:48pitrousetmessages: + msg97061
versions: + Python 3.2, - Python 3.0
2009-12-30 19:36:27giampaolo.rodolasetnosy: + pitrou
2009-01-08 08:33:54vstinnersetfiles: - ftplib.patch
2009-01-08 01:53:48giampaolo.rodolasetfiles: + ftplib.patch
messages: + msg79392
2009-01-08 01:10:26vstinnersetnosy: + vstinner
messages: + msg79390
2009-01-03 00:52:13giampaolo.rodolacreate