diff options
Diffstat (limited to 'includes/bootstrap.inc')
-rw-r--r-- | includes/bootstrap.inc | 30 |
1 files changed, 22 insertions, 8 deletions
diff --git a/includes/bootstrap.inc b/includes/bootstrap.inc index c3f553793..da33a88f2 100644 --- a/includes/bootstrap.inc +++ b/includes/bootstrap.inc @@ -347,11 +347,6 @@ function conf_path($require_settings = TRUE, $reset = FALSE) { } $uri = explode('/', $_SERVER['SCRIPT_NAME'] ? $_SERVER['SCRIPT_NAME'] : $_SERVER['SCRIPT_FILENAME']); - if (strpos($_SERVER['HTTP_HOST'], '/') !== FALSE || strpos($_SERVER['HTTP_HOST'], '\\') !== FALSE) { - // A HTTP_HOST containing slashes may be an attack and is invalid. - header($_SERVER['SERVER_PROTOCOL'] . ' 400 Bad Request'); - exit; - } $server = explode('.', implode('.', array_reverse(explode(':', rtrim($_SERVER['HTTP_HOST'], '.'))))); for ($i = count($uri) - 1; $i > 0; $i--) { for ($j = count($server); $j > 0; $j--) { @@ -386,6 +381,21 @@ function drupal_initialize_variables() { } /** + * Validate that $_SERVER['HTTP_HOST'] is safe. + * + * As $_SERVER['HTTP_HOST'] is user input, ensure it only contains characters + * allowed in hostnames. See RFC 952 (and RFC 2181). $_SERVER['HTTP_HOST'] is + * lowercased. + * + * @return + * TRUE if only containing valid characters, or FALSE otherwise. + */ +function drupal_valid_http_host() { + $_SERVER['HTTP_HOST'] = strtolower($_SERVER['HTTP_HOST']); + return preg_match('/^\[?(?:[a-z0-9-:\]_]+\.?)+$/', $_SERVER['HTTP_HOST']); +} + +/** * Loads the configuration and sets the base URL, cookie domain, and * session name correctly. */ @@ -396,6 +406,12 @@ function conf_init() { global $databases, $db_prefix, $cookie_domain, $conf, $installed_profile, $update_free_access; $conf = array(); + if (!drupal_valid_http_host()) { + // HTTP_HOST is invalid, e.g. if containing slashes it may be an attack. + header($_SERVER['SERVER_PROTOCOL'] . ' 400 Bad Request'); + exit; + } + if (file_exists(DRUPAL_ROOT . '/' . conf_path() . '/settings.php')) { include_once DRUPAL_ROOT . '/' . conf_path() . '/settings.php'; } @@ -414,9 +430,7 @@ function conf_init() { // Create base URL $base_root = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on') ? 'https' : 'http'; - // As $_SERVER['HTTP_HOST'] is user input, ensure it only contains - // characters allowed in hostnames. - $base_url = $base_root .= '://' . preg_replace('/[^a-z0-9-:._]/i', '', $_SERVER['HTTP_HOST']); + $base_url = $base_root .= '://' . $_SERVER['HTTP_HOST']; // $_SERVER['SCRIPT_NAME'] can, in contrast to $_SERVER['PHP_SELF'], not // be modified by a visitor. |