Bug #64457 [Com]: HTTP_HOST, SERVER_NAME, SERVER_PORT spoofing
| From: | dm@php.net | Date: | Tue, 19 Mar 2013 19:38:43 +0000 |
| Subject: | Bug #64457 [Com]: HTTP_HOST, SERVER_NAME, SERVER_PORT spoofing | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-177909@lists.php.net to get a copy of this message | ||
Edit report at https://bugs.php.net/bug.php?id=64457&edit=1
ID: 64457
Comment by: dm@php.net
Reported by: dm@php.net
Summary: HTTP_HOST, SERVER_NAME, SERVER_PORT spoofing
Status: Analyzed
Type: Bug
Package: Apache2 related
Operating System: All
PHP Version: Irrelevant
Block user comment: N
Private report: N
New Comment:
Indeed, it's not a PHP issue per se, and I'm glad, thank you.
I'm aware that $_SERVER['HTTP_*'] are passed on, but what about
$_SERVER['SERVER_*'] (or you meant everything web server related)?
Why would Apache not know what is the hostname and which port is it serving through?
Nginx and some variations of Apache (haven't tried sending HTTP 1.0 request) settings
don't have this "problem".
RFC 2616 states that 1.1 requests specifying a hostname not in use by the server should receive a
400 Bad Request response, which is sometimes (I don't know when exactly) is not the case.
Thanks.
Previous Comments:
------------------------------------------------------------------------
[2013-03-19 19:16:48] rasmus@php.net
But how is this a PHP issue? PHP doesn't set the $_SERVER['HTTP_*"] variables at
all. They are inherited directly from the web server and are the same variables
that the web server would set for CGI scripts that might get executed. So while
we could try to do some analysis and filtering at the PHP level, anything else
the web server invokes would still be getting the spoofed port. The fix should be
at the web server level.
------------------------------------------------------------------------
[2013-03-19 19:03:42] dm@php.net
Description:
------------
HTTP_HOST is the value from Host header, which can, naturally, be spoofed.
On the other hand, SERVER_NAME and SERVER_PORT should reflect real values.
I've tested some configurations and on majority you can at least change/spoof
SERVER_PORT.
This can lead to security issues since these environment variables are often trusted.
Test script:
---------------
<?php
$ch = curl_init('http://smchiptuning.com/http_host.php');
curl_setopt($ch, CURLOPT_HTTPHEADER, array('Host: 127.0.0.1:1337'));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
echo curl_exec($ch);
curl_close($ch);
/**
http_host.php
<?php
var_dump($_SERVER['SERVER_NAME'], $_SERVER['SERVER_PORT']);
*/
Expected result:
----------------
string(16) "smchiptuning.com" string(2) "80"
Actual result:
--------------
string(9) "127.0.0.1" string(4) "1337"
------------------------------------------------------------------------
--
Edit this bug report at https://bugs.php.net/bug.php?id=64457&edit=1