The very simple attached patch adds an option to disable POST data processing, which implies the data can only be read in a stream fashion through php://input.

As far as I know, PHP offers no way to inhibit processing RFC 1867 data and one has to use very hacky means to accomplish that. This is often required (or at least convenient) in order to, e.g., proxy requests or handle file uploads in memory.

For other types of requests, the default processing of POST data may also be a problem. Take a non-application/x-www-form-urlencoded POST requests (say, some kind of RPC with a big XML payload) -- PHP is very memory inefficient as it will hold the whole POST data into memory and duplicate it twice (from SG(request_info).post_data to $HTTP_RAW_POST_DATA -- even if always_populate_raw_post_data=0 -- and SG(request_info).raw_post_data).

This introduces a new ini setting, disable_post_data_processing, but it's a benign one. No incompatibilities between setups will arise because no one will enable it globally (it would be insane), only selectively to the scripts that require it. The reason for an ini setting is that it must be set early in the request life.

Thoughts?

--
Gustavo Lopes
Index: main/main.c
===================================================================
--- main/main.c (revision 305891)
+++ main/main.c (working copy)
@@ -491,6 +491,7 @@
        STD_PHP_INI_BOOLEAN("allow_url_fopen",          "1",            
PHP_INI_SYSTEM,         OnUpdateBool,           allow_url_fopen,                
php_core_globals,               core_globals)
        STD_PHP_INI_BOOLEAN("allow_url_include",        "0",            
PHP_INI_SYSTEM,         OnUpdateBool,           allow_url_include,              
php_core_globals,               core_globals)
        STD_PHP_INI_BOOLEAN("always_populate_raw_post_data",    "0",    
PHP_INI_SYSTEM|PHP_INI_PERDIR,  OnUpdateBool,   always_populate_raw_post_data,  
php_core_globals,       core_globals)
+       STD_PHP_INI_BOOLEAN("disable_post_data_processing",     "0",    
PHP_INI_SYSTEM|PHP_INI_PERDIR,  OnUpdateBool,   disable_post_data_processing,   
php_core_globals,       core_globals)
 
        STD_PHP_INI_ENTRY("realpath_cache_size",        "16K",          
PHP_INI_SYSTEM,         OnUpdateLong,   realpath_cache_size_limit,      
virtual_cwd_globals,    cwd_globals)
        STD_PHP_INI_ENTRY("realpath_cache_ttl",         "120",          
PHP_INI_SYSTEM,         OnUpdateLong,   realpath_cache_ttl,                     
virtual_cwd_globals,    cwd_globals)
Index: main/php_globals.h
===================================================================
--- main/php_globals.h  (revision 305891)
+++ main/php_globals.h  (working copy)
@@ -133,6 +133,7 @@
        zend_bool during_request_startup;
        zend_bool allow_url_fopen;
        zend_bool always_populate_raw_post_data;
+       zend_bool disable_post_data_processing;
        zend_bool report_zend_debug;
 
        int last_error_type;
Index: main/SAPI.c
===================================================================
--- main/SAPI.c (revision 305891)
+++ main/SAPI.c (working copy)
@@ -393,7 +393,7 @@
 
        /* handle request mehtod */
        if (SG(server_context)) {
-               if ( SG(request_info).request_method) {
+               if (!PG(disable_post_data_processing) && 
SG(request_info).request_method) {
                        if(!strcmp(SG(request_info).request_method, "POST")
                           && (SG(request_info).content_type)) {
                                /* HTTP POST -> may contain form data to be 
read into variables
Index: tests/basic/disable_post_data_processing_01.phpt
===================================================================
--- tests/basic/disable_post_data_processing_01.phpt    (revision 0)
+++ tests/basic/disable_post_data_processing_01.phpt    (revision 0)
@@ -0,0 +1,22 @@
+--TEST--
+disable_post_data_processing: basic test
+--INI--
+disable_post_data_processing=1
+--POST_RAW--
+Content-Type: application/x-www-form-urlencoded
+a=1&b=ZYX
+--FILE--
+<?php
+var_dump($_FILES);
+var_dump($_POST);
+var_dump($HTTP_RAW_POST_DATA);
+var_dump(file_get_contents("php://input"));
+--EXPECTF--
+array(0) {
+}
+array(0) {
+}
+
+Notice: Undefined variable: HTTP_RAW_POST_DATA in %s on line %d
+NULL
+string(9) "a=1&b=ZYX"

Property changes on: tests\basic\disable_post_data_processing_01.phpt
___________________________________________________________________
Added: svn:keywords
   + Id Rev Revision Date LastChangedDate LastChangedRevision Author 
LastChangedBy HeadURL URL
Added: svn:eol-style
   + native

Index: tests/basic/disable_post_data_processing_02.phpt
===================================================================
--- tests/basic/disable_post_data_processing_02.phpt    (revision 0)
+++ tests/basic/disable_post_data_processing_02.phpt    (revision 0)
@@ -0,0 +1,28 @@
+--TEST--
+disable_post_data_processing: rfc1867
+--INI--
+disable_post_data_processing=1
+--POST_RAW--
+Content-Type: multipart/form-data; 
boundary=---------------------------20896060251896012921717172737
+-----------------------------20896060251896012921717172737
+Content-Disposition: form-data; name="file1"; filename="file1.txt"
+Content-Type: text/plain-file
+
+1
+-----------------------------20896060251896012921717172737--
+--FILE--
+<?php
+var_dump($_FILES);
+var_dump($_POST);
+var_dump(file_get_contents("php://input"));
+--EXPECTF--
+array(0) {
+}
+array(0) {
+}
+string(224) "-----------------------------20896060251896012921717172737
+Content-Disposition: form-data; name="file1"; filename="file1.txt"
+Content-Type: text/plain-file
+
+1
+-----------------------------20896060251896012921717172737--"

Property changes on: tests\basic\disable_post_data_processing_02.phpt
___________________________________________________________________
Added: svn:keywords
   + Id Rev Revision Date LastChangedDate LastChangedRevision Author 
LastChangedBy HeadURL URL
Added: svn:eol-style
   + native

Index: tests/basic/disable_post_data_processing_03.phpt
===================================================================
--- tests/basic/disable_post_data_processing_03.phpt    (revision 0)
+++ tests/basic/disable_post_data_processing_03.phpt    (revision 0)
@@ -0,0 +1,23 @@
+--TEST--
+disable_post_data_processing: always_populate_raw_post_data has no effect (1)
+--INI--
+disable_post_data_processing=1
+always_populate_raw_post_data=1
+--POST_RAW--
+Content-Type: application/x-www-form-urlencoded
+a=1&b=ZYX
+--FILE--
+<?php
+var_dump($_FILES);
+var_dump($_POST);
+var_dump($HTTP_RAW_POST_DATA);
+var_dump(file_get_contents("php://input"));
+--EXPECTF--
+array(0) {
+}
+array(0) {
+}
+
+Notice: Undefined variable: HTTP_RAW_POST_DATA in %s on line %d
+NULL
+string(9) "a=1&b=ZYX"

Property changes on: tests\basic\disable_post_data_processing_03.phpt
___________________________________________________________________
Added: svn:keywords
   + Id Rev Revision Date LastChangedDate LastChangedRevision Author 
LastChangedBy HeadURL URL
Added: svn:eol-style
   + native

Index: tests/basic/disable_post_data_processing_04.phpt
===================================================================
--- tests/basic/disable_post_data_processing_04.phpt    (revision 0)
+++ tests/basic/disable_post_data_processing_04.phpt    (revision 0)
@@ -0,0 +1,23 @@
+--TEST--
+disable_post_data_processing: always_populate_raw_post_data has no effect (2)
+--INI--
+disable_post_data_processing=1
+always_populate_raw_post_data=1
+--POST_RAW--
+Content-Type: application/unknown
+a=1&b=ZYX
+--FILE--
+<?php
+var_dump($_FILES);
+var_dump($_POST);
+var_dump($HTTP_RAW_POST_DATA);
+var_dump(file_get_contents("php://input"));
+--EXPECTF--
+array(0) {
+}
+array(0) {
+}
+
+Notice: Undefined variable: HTTP_RAW_POST_DATA in %s on line %d
+NULL
+string(9) "a=1&b=ZYX"

Property changes on: tests\basic\disable_post_data_processing_04.phpt
___________________________________________________________________
Added: svn:keywords
   + Id Rev Revision Date LastChangedDate LastChangedRevision Author 
LastChangedBy HeadURL URL
Added: svn:eol-style
   + native


-- 
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to