-
Notifications
You must be signed in to change notification settings - Fork 7.7k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fix GH-10562: Memory leak and invalid state with consecutive ftp_nb_fget
When the user does not fully consume the data stream, but instead opens a new one, a memory leak occurs. Moreover, the state is invalid: when more commands arrive they'll be handled out-of-sync because the state of the client does not match what the server is doing. This leads to all sorts of weirdness, for example: Warning: ftp_nb_fget(): OK. Fix it by gracefully closing the old data stream when a new data stream is started. Closes GH-11606.
- Loading branch information
Showing
3 changed files
with
51 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
--TEST-- | ||
GH-10562 (Memory leak with consecutive ftp_nb_fget) | ||
--EXTENSIONS-- | ||
ftp | ||
pcntl | ||
--FILE-- | ||
<?php | ||
require 'server.inc'; | ||
|
||
$ftp = ftp_connect('127.0.0.1', $port); | ||
if (!$ftp) die("Couldn't connect to the server"); | ||
|
||
var_dump(ftp_login($ftp, 'anonymous', 'IEUser@')); | ||
|
||
$local_file = __DIR__ . DIRECTORY_SEPARATOR . "gh10562.txt"; | ||
$fout = fopen($local_file, "w"); | ||
|
||
// This requests more data, but we don't do the loop to fetch it. | ||
$ret = ftp_nb_fget($ftp, $fout, "fget", FTP_BINARY, 0); | ||
var_dump($ret == FTP_MOREDATA); | ||
|
||
// This aborts the previous request, fetches the whole "a story" file. | ||
$ret = ftp_nb_fget($ftp, $fout, "a story", FTP_BINARY, 0); | ||
while ($ret == FTP_MOREDATA) { | ||
$ret = ftp_nb_continue($ftp); | ||
} | ||
|
||
fclose($fout); | ||
|
||
echo file_get_contents($local_file), "\n"; | ||
?> | ||
--CLEAN-- | ||
<?php | ||
@unlink(__DIR__ . DIRECTORY_SEPARATOR . "gh10562.txt"); | ||
?> | ||
--EXPECT-- | ||
bool(true) | ||
bool(true) | ||
BINARYFooBar | ||
For sale: baby shoes, never worn. |