php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #61665 include on stream wrapper results in wsod
Submitted: 2012-04-08 09:56 UTC Modified: 2013-02-18 00:35 UTC
Votes:2
Avg. Score:5.0 ± 0.0
Reproduced:1 of 1 (100.0%)
Same Version:0 (0.0%)
Same OS:0 (0.0%)
From: btmash at gmail dot com Assigned:
Status: No Feedback Package: Streams related
PHP Version: 5.3.10 OS: Ubuntu 10.04
Private report: No CVE-ID: None
View Add Comment Developer Edit
Welcome! If you don't have a Git account, you can't do anything here.
You can add a comment by following this link or if you reported this bug, you can edit this bug over here.
(description)
Block user comment
Status: Assign to:
Package:
Bug Type:
Summary:
From: btmash at gmail dot com
New email:
PHP Version: OS:

 

 [2012-04-08 09:56 UTC] btmash at gmail dot com
Description:
------------
Hi,

I am currently running a drupal website using a module (http://drupal.org/project/configuration) that provided its own contributed stream wrapper to find the local configuration directory (so it was in the format 'config://path/to/file' - the implementation can be seen at http://drupalcode.org/project/configuration.git/blob/refs/heads/7.x-1.x:/configuration_stream.inc). On my local environment of running the site with the module (which runs php 5.3.6), the configuration would be able to scan on files with the protocol without any issues. 

However, once I moved to my staging environment which runs php 5.3.10, I would end up with a wsod. The strange part was that the page returned a code 200 and nothing in the error log. I made sure that allow_url_fopen was enabled and the protocols actually registered so it should have worked correctly. Moreover, using file_exists and is_file work to ensure the file exists so that meant the file was being found the first time around.

For now, my workaround has been to use drupal's functions to get the stream converted correctly (see http://drupal.org/files/config-stream.patch as my workaround for the module to work) but problem seems to stem from PHP which is why I am filing my issue here. Any help that can be provided would be greatly appreciated.

Test script:
---------------
Implement a simple stream wrapper to a file in local (lets call it local).

Create a php file to include from somewhere (called test_include.inc).

Have the line 'include local://path/to/test_include.inc'.

Expected result:
----------------
It should result in a code 200 but also a wsod.

Actual result:
--------------
The script should be correctly included.

Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2012-04-09 22:12 UTC] cataphract@php.net
Please include the code of the stream wrapper, otherwise we can't reproduce this problem. In particular, the implementation of stream_open would be very important (but please include everything).
 [2012-04-09 22:12 UTC] cataphract@php.net
-Status: Open +Status: Feedback
 [2012-04-09 23:29 UTC] btmash at gmail dot com
I've pasted a version of the class at http://paste.pocoo.org/show/578721/ since it is longer than 20 lines.

Please note that a large chunk of this is the drupal stream wrapper interface and at the bottom is the stream class that I implemented 'MyLocalStreamWrapper' which returns back the directory it is currently in. I perform an include to a info.php file which consists of:
"
<?php

phpinfo();

"

I tested this out on PHP 5.3.8 and it worked. When I tested this on 5.3.10, it failed.
 [2012-04-19 08:08 UTC] btmash at gmail dot com
I'm setting it back to open since I've provided feedback.
 [2012-04-19 08:08 UTC] btmash at gmail dot com
-Status: Feedback +Status: Open
 [2012-06-28 00:56 UTC] pollita@php.net
Hi, could you paste the wrapper code again? That link is invalid (the content 
hosting site went down).  Thanks!
 [2012-06-28 00:56 UTC] pollita@php.net
-Status: Open +Status: Feedback
 [2013-02-18 00:35 UTC] php-bugs at lists dot php dot net
No feedback was provided. The bug is being suspended because
we assume that you are no longer experiencing the problem.
If this is not the case and you are able to provide the
information that was requested earlier, please do so and
change the status of the bug back to "Open". Thank you.
 [2015-02-09 04:42 UTC] dave dot qt080 at davehw dot dircon dot co dot uk
The following script works fine on 5.3.4 but fails with this bug on 5.3.29.
I have attached the script together with the output from each of these PHP versions.

<?
/**
 * Stream wrapper class that enables contents of dataContainer::$streamedData variable to be 'included'
 */
class EvaleratorStream {
    var $position=0;
    public function stream_open($path, $mode, $options, &$opened_path)
    	{
    	echo '** stream_open called<BR/>';
        $this->position = 0;
        return true;
    	}
    public function stream_read($count)
    	{
    	echo '** stream_read called<BR/>';
        $ret = substr(dataContainer::$streamedData,$this->position,$count);
        $this->position += strlen($ret);
        return $ret;
    	}
    public function stream_write($data)
    	{ //Not implemented
    	echo '** stream_write called<BR/>';
        return strlen($data);
    	}
	public function stream_tell()
    	{
    	echo '** stream_tell called<BR/>';
        return $this->position;
    	}
    public function stream_eof()
	{
    	echo '** stream_eof called<BR/>';
        return $this->position>=strlen(dataContainer::$streamedData);
    	}
    public function stream_seek($offset, $whence)
	{
    	echo '** stream_seek called<BR/>';
        switch ($whence) 
            {
            case SEEK_SET:
                if ($offset<strlen(dataContainer::$streamedData) && $offset>=0) 
                    {
                    $this->position = $offset;
                    return true;
                    } 
                return false;
            case SEEK_CUR:
                if ($offset >= 0) 
                    {
                    $this->position += $offset;
                    return true;
                    }
                return false;
            case SEEK_END:
                if (strlen(dataContainer::$streamedData) + $offset>=0) 
                    {
                    $this->position= strlen(dataContainer::$streamedData)+$offset;
                    return true;
                    }
                return false;
	    default:
                return false;
            }
    	}
    public function stream_metadata($path, $option, $var) 
    	{
    	echo '** stream_metadata called<BR/>';
        if($option==STREAM_META_TOUCH)
            return true;
        return false;
    	}
    public function stream_stat()
   	{
    	echo '** stream_stat called<BR/>';
   		return array(7=>strlen(dataContainer::$streamedData),
   					 'size'=>strlen(dataContainer::$streamedData));	
   	}
    public function  stream_close()
	{
    	echo '** stream_close called<BR/>';
	}
    //The following functions should not be required, but are included 
    // with echo's, just so we can see if they get called
    public function dir_closedir()
    	{
    	echo '** dir_closedir called<BR/>';
    	return true;	
    	}
    public function dir_opendir($path,$options)
	{
    	echo '** dir_opendir called<BR/>';
    	return true;	
	}
    public function dir_readdir()
	{
    	echo '** dir_readdir called<BR/>';
    	return '';	
	}
    public function dir_rewinddir()
	{
    	echo '** dir_rewinddir called<BR/>';
    	return true;
	}
    public function mkdir($path,$mode,$options)
	{
    	echo '** mkdir called<BR/>';
    	return true;
	}
    public function rename($path_from,$path_to)
	{
    	echo '** rename called<BR/>';
    	return true;
	}
    public function rmdir($path,$options)
	{
    	echo '** rmdir called<BR/>';
    	return true;
	}
    public function stream_cast($cast_as)
	{
    	echo '** stream_cast called<BR/>';
    	return false;
	}
    public function stream_flush()
	{
    	echo '** stream_flush called<BR/>';
    	return true;
	}
    public function stream_lock($operation)
	{
    	echo '** stream_lock called<BR/>';
    	return true;
	}
    public function stream_set_option ($option,$arg1,$arg2)
	{
    	echo '** stream_set_option called<BR/>';
    	return true;
	}
    public function stream_truncate ($new_size)
	{
    	echo '** stream_truncate called<BR/>';
    	return true;
	}
    public function unlink ($path)
	{
    	echo '** unlink called<BR/>';
    	return true;
	}
    public function url_stat($path,$flags)
	{
        echo '** url_stat called<BR/>';
    	return array();
	}	
    }
	
class dataContainer
    {
    public static $streamedData;
    }

error_reporting(E_ALL);	
if (!stream_wrapper_register("var", "EvaleratorStream"))
    trigger_error("Unable to register stream wrapper", E_USER_ERROR);
echo 'registered ok<BR/>';

//Initialise the streamed data with a simple script containing 
// a PHP echo statement
dataContainer::$streamedData='<?echo "Yay - Executing streamed script!<BR/>";?>';
echo 'data stored<BR/>';

//Try to read and print the stream
$file=fopen("var://streamedData",'r');
if ($file===false)
    {
    echo 'file open failed';
    exit;
    }
echo 'stream was opened ok<BR/>';
$data=fgets($file);
echo 'stream data='.htmlspecialchars($data).'<BR/>';
fclose($file);
echo 'stream closed ok<BR/>';

//Try to include the streamed script so it gets executed
//  At this point, PHP 5.3.4 executes the script correctly and the 'Yay' message is echoed
//  In contrast, PHP 5.3.29 dies with nothing at all displayed after the 'stream closed ok' 
 
include "var://streamedData";
	
echo 'end<BR/>';
?>

OUTPUT FROM PHP 5.3.4:
registered ok
data written
** stream_open called
stream was opened ok
** stream_read called
** stream_eof called
stream data=<?echo "Yay - Executing streamed script!<BR/>";?>
** stream_flush called
** stream_close called
stream closed ok
** stream_open called
** stream_stat called
** stream_stat called
** stream_read called
** stream_eof called
** stream_read called
** stream_eof called
** stream_flush called
** stream_close called
Yay - Executing streamed script!
end

OUTPUT FROM PHP 5.3.29:
registered ok
data written
** stream_open called
stream was opened ok
** stream_read called
** stream_eof called
stream data=<?echo "Yay - Executing streamed script!<BR/>";?>
** stream_flush called
** stream_close called
stream closed ok
 
PHP Copyright © 2001-2020 The PHP Group
All rights reserved.
Last updated: Fri Dec 04 18:01:23 2020 UTC