Bug #67905 [Opn->Ver]: proc_open leaks file descriptors on error
| From: | gwynne@php.net | Date: | Thu, 18 Sep 2014 14:21:25 +0000 |
| Subject: | Bug #67905 [Opn->Ver]: proc_open leaks file descriptors on error | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-187590@lists.php.net to get a copy of this message | ||
Edit report at https://bugs.php.net/bug.php?id=67905&edit=1
ID: 67905
Updated by: gwynne@php.net
Reported by: jille at hexon dot cx
Summary: proc_open leaks file descriptors on error
-Status: Open
+Status: Verified
Type: Bug
Package: Program Execution
Operating System: n/a
PHP Version: master-Git-2014-08-26 (Git)
Block user comment: N
Private report: N
New Comment:
Confirmed that this bug still stands. A test which shows the failure directly:
<?php
// This test requires a /dev/fd filesystem (OS X for example) to show the error.
// There should only be 4 descriptors (stdin, stdout, stderr, readdir of /dev/fd) open after the
failed proc_open().
proc_open("/bin/true", [0 => ['pipe', 'r'], 1 =>
['INVALID']], $pipes);
print_r(scandir("/dev/fd"));
?>
Correct fix is to move this code from the fork() failure case to the error_exit case:
for (i = 0; i < ndesc; i++) {
close(descriptors[i].childend);
if (descriptors[i].parentend >= 0)
close(descriptors[i].parentend);
}
(Please note - the fork() failure case does not check >= 0, which can cause a leaked descriptor
if stdin was closed before proc_open() was called.)
Previous Comments:
------------------------------------------------------------------------
[2014-08-26 07:59:45] jille at hexon dot cx
Description:
------------
proc_open leaks file descriptors when leaving via the exit_fail label. There is some code to clean
them up, but it is only executed when fork() fails instead of opening one of the descriptors.
References:
https://github.com/php/php-src/blob/c3e3c98/ext/standard/proc_open.c#L512
(goto)
https://github.com/php/php-src/blob/c3e3c98/ext/standard/proc_open.c#L952
(label)
https://github.com/php/php-src/blob/c3e3c98/ext/standard/proc_open.c#L852
(fork failed)
Test script:
---------------
<?php
$descr = array(
0 => array('file', '/dev/null', 'r'),
1 => array('file', '/nonexistent', 'r'),
);
for($i = 0; 1025 > $i; $i++) {
$ph = proc_open('true', $descr, $pipes);
}
?>
------------------------------------------------------------------------
--
Edit this bug report at https://bugs.php.net/bug.php?id=67905&edit=1