Nginx-Host绕过复现

文章介绍了Nginx和PHP处理Host头的不同方式,导致的安全隐患,包括Nginx的冒号分割策略,多Host头的情况,以及HTTPS中的SNI利用。通过三种处理方式展示了如何可能绕过服务器配置限制,触发SQL报错或访问非预期服务器块。
摘要由CSDN通过智能技术生成

目录

环境搭建:

第一种处理方式

第二种处理方式

第三种处理方式


原理依据:Nginx与PHP对Host处理方式不同

环境搭建:

1、提前安装完成nginx+php+mysql,然后上传文件pwnhub到nginx/html下

2、修改nginx.conf配置文件:

    server {
        listen          80;
        server_name     www.php.com;
        root            html/pwnhub/web;
        index           index.html index.php index.htm;
        #location / {
        #    root       html/mhz/web;
        #    index      index.html index.htm index.php;
        #}
        location / {
        try_files $uri $uri/ /index.php;
        }
        location ~ \.php(.*)$ {
            fastcgi_pass        127.0.0.1:9000;
            fastcgi_index       index.php;
            fastcgi_split_path_info ^((?U).+\.php)(/?.+)$;
            fastcgi_param       SCRIPT_FILENAME $document_root$fastcgi_script_name;
            fastcgi_param       PATH_INFO $fastcgi_path_info;
            fastcgi_param       PATH_TRANSLATED $document_root$fastcgi_path_info;
            include             fastcgi_params;
        }
    }

3、在nginx/sbin目录下运行

./nginx -s reload

4、运行MySQL数据库并创建数据库和表:

[root@localhost ~]# mysql -u root -p
Enter password: 
​
mysql> show databases;
mysql> create database security;
mysql> use security;
​
mysql>SET NAMES utf8;
mysql>SET FOREIGN_KEY_CHECKS = 0;
​
mysql>DROP TABLE IF EXISTS `flags`;
mysql>CREATE TABLE `flags` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `flag` varchar(256) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8mb4;
​
mysql>DROP TABLE IF EXISTS `users`;
mysql>CREATE TABLE `users` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `username` varchar(256) NOT NULL,
  `password` varchar(32) NOT NULL,
  `email` varchar(256) DEFAULT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `username` (`username`)
) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=utf8mb4;
​
mysql>SET FOREIGN_KEY_CHECKS = 1;

5、在本地“C:\Windows\System32\drivers\etc/hosts”中添加映射关系。

6、在本地浏览器中访问“www.php.com”,便可以看到如下图片,默认登录页面地址为“http://www.php.com/main/login”,

 

切换为“http://www.php.com/main/register”就可以注册新用户,如下图所示

 

第一种处理方式

Nginx在处理Host的时候,会将Host用冒号分割成hostname和port,port部分被丢弃。所以,我们可以设置Host的值为www.php.com:xxx'"@example.com,这样就能访问到目标Server块:

 

如上图,成功触发SQL报错。

总结:Nginx通过冒号分隔只截取到冒号之前的内容,而PHP会将全部内容都拿到。

第二种处理方式

当我们传入两个Host头的时候,Nginx将以第一个为准,而PHP-FPM将以第二个为准。

Host:www.php.com
Host:xxx'"@example.com

Nginx将认为Host为www.php.com并交给Server处理;但是PHP中使用$_SERVER['HTTP_HOST']取到的值却是xxx'"@example.com。这种方法也可以实现绕过。

 

注意:只有Nginx+PHP会出现这个问题,Apache与此不同,将会是另一种情况。

第三种处理方式

原理:在发送https数据包的时候,SNI中指定的域名是example2.com,而无需和HTTP报文中的Host头保持一致,Nginx会选择SNI中的域名作为Server Name。

 

我们可以直接使用Burpsuite来测试这个trick,比如我在后端编写PHP代码echo $_SERVER['HTTP_HOST']。正常访问是会显示此时的Host头。

在HTTP协议时,如果我们修改Host头,Nginx将因为识别不到Server Name被导向默认的页面。

但此时我们在Burpsuite里修改协议为https,并指定好https的Host,也就是SNI,如图4。我们再修改HTTP数据包的Host头,就能正常访问目标后端了。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值