php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #75776 Flushing streams with compression filter is broken
Submitted: 2018-01-08 03:27 UTC Modified: 2021-02-16 18:02 UTC
From: shestero at meta dot ua Assigned: cmb (profile)
Status: Closed Package: Streams related
PHP Version: 7.0.27 OS: Debian
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: shestero at meta dot ua
New email:
PHP Version: OS:

 

 [2018-01-08 03:27 UTC] shestero at meta dot ua
Description:
------------
I used this way to produce compressed output for years but now it return zero-output without any errors anywhere.

Registered Stream Filters:	zlib.*, bzip2.*, convert.iconv.*, mcrypt.*, mdecrypt.*, string.rot13, string.toupper, string.tolower, string.strip_tags, convert.*, consumed, dechunk

My configure parameters:
'./configure' '--with-openssl' '--with-ssl=/usr/bin/openssl' '--with-ssl-lib=/usr/lib/x86_64-linux-gnu' '--with-libdir=lib/x86_64-linux-gnu' '--with-bz2' '--enable-exif' '--with-gd' '--with-mcrypt' '--with-mysql' '--with-mysql-sock' '--enable-sockets' '--enable-zip' '--with-apxs2=/usr/bin/apxs2' '--with-config-file-path=/var/lib/apache2/conf' '--with-jpeg-dir' '--enable-gd-native-ttf' '--with-xmlrpc' '--with-freetype-dir' '--with-zlib' '--with-zlib-dir' '--enable-maintainer-zts' '--with-tsrm-pthreads' '--with-mysqli' '--enable-mbstring' '--with-pdo-mysql=mysqlnd' '--with-mysqli=mysqlnd' '--with-curl' '--enable-memcache'

PS Output mute as I adding compression filters. string.toupper and string.tolower work!

Test script:
---------------
error_reporting(E_ALL); ini_set("display_errors", 1);
	if (true)
	{
	  header("Content-Description: File Transfer");
	  header("Content-Disposition: attachment; filename=main.csv.bz2");
	  header("Content-Type: application/x-bzip2");
	  header("Content-Transfer-Encoding: binary");
	}
	else
	{
	  header("Content-Type: application/csv");
	  header("Content-Disposition: attachment;Filename=main.csv");
	}

	$bz = fopen('php://output', 'w');

fwrite($bz,"sdfgdfg"); // output such way
...
fflush($bz); 
fclose($bz);

	stream_filter_append($bz, 'convert.iconv.UTF-8/CP1251//TRANSLIT'); // ok

	if (true)
	{
	  $param = array('blocks' => 6, 'work' => 0); // for bzip2
	  $ok = stream_filter_append($bz, 'bzip2.compress', STREAM_FILTER_WRITE, $param);
	  // $param = array('level' => 6, 'window' => 15, 'memory' => 9); // for gzip
	  //$ok = stream_filter_append($bz, 'zlib.deflate');//, STREAM_FILTER_WRITE, $param);
	  if ($ok===false)
	  {
	    die("Cannot stream_filter_append( 'bzip2.compress' ) !");
	  }
	}

Expected result:
----------------
error or some output as usual

Actual result:
--------------
browser saves zero-size file.

Patches

Pull Requests

Pull requests:

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2018-01-08 03:30 UTC] shestero at meta dot ua
PS
fwrite($bz,"sdfgdfg"); // output such way
...
fflush($bz); 
fclose($bz);

of cause at the end.
The existing code used about 5-6 years with different PHP versions so I'm quite sure it's ok.
 [2018-01-09 14:37 UTC] mike@php.net
-Status: Open +Status: Verified
 [2018-01-09 14:37 UTC] mike@php.net
Seems to be caused by the fflush() call.
 [2018-01-10 02:08 UTC] shestero at meta dot ua
Yes.
Really commenting fflush solves the problem?

But what's wrong with fflush? I process data streaming and sometimes fill it should be flushed after some portion is over.
 [2018-01-10 02:09 UTC] shestero at meta dot ua
Commenting fflush solves the problem. I checked.
 [2021-02-15 14:08 UTC] cmb@php.net
-Package: *Compression related +Package: Streams related
 [2021-02-15 14:08 UTC] cmb@php.net
With regard to zlib.deflate this is a duplicate of bug #48725,
which is fixed as of PHP 7.4.14 and 8.0.1, respectively, but
apparently bzip2.compress has the same problem.

Recatogorizing as "streams related" since "filter related" is
used too often for ext/filter.
 [2021-02-16 18:02 UTC] cmb@php.net
-Summary: compression filters on stdout not working any more +Summary: Flushing streams with compression filter is broken -Assigned To: +Assigned To: cmb
 [2021-02-16 18:02 UTC] cmb@php.net
While having a closer look at the bzip2 issue, I noticed that the
fix for the other bug does not fully resolve the flushing issue
for zlib compression streams.

Anyhow, this is not particularly related to php://output streams,
but affects streams generally.  Furthermore, not only fflush()
triggers the misbehavior, but also other function calls, such as
rewind(), which flush the stream internally.
 [2021-02-16 18:45 UTC] cmb@php.net
The following pull request has been associated:

Patch Name: Fix #75776: Flushing streams with compression filter is broken
On GitHub:  https://github.com/php/php-src/pull/6703
Patch:      https://github.com/php/php-src/pull/6703.patch
 [2021-02-22 14:35 UTC] cmb@php.net
Automatic comment on behalf of cmbecker69@gmx.de
Revision: http://git.php.net/?p=php-src.git;a=commit;h=963e50c8c48ecfbe7444445e5ca8e33530d630d0
Log: Fix #75776: Flushing streams with compression filter is broken
 [2021-02-22 14:35 UTC] cmb@php.net
-Status: Verified +Status: Closed
 
PHP Copyright © 2001-2025 The PHP Group
All rights reserved.
Last updated: Tue Apr 01 19:01:31 2025 UTC