很多时候我们为网站套上Cloudflare等CDN服务最基础的目的之一:隐藏源站服务器IP;防止弱小可怜又无助的源站直面狂轰滥炸、无所不用其极的恶意攻击,这里我们先说说为什么接入CDN后依然存在源站IP泄露问题以及如何快速找源站IP;两个主要方向:入站扫描以及出站访问;其次还有第三方因素:互联网上大量自动化爬虫,历史解析记录缓存导致源站服务器IP泄露。

入站扫描源站IP的原理以及成因说明

1,我们在浏览器输入域名,浏览器通过HTTP/s协议访问具体网站,其中底层的通讯实质是:DNS解析域名获得IP,以IP+端口(HTTP默认端口:80、HTTPS默认端口:443)+HOST(域名)形式根据HTTP/S协议标准封装为TCP数据包向源站获取网站内容,这里我们使用Curl命令查看HTTP请求过程以及结构:
curl -svo /dev/null http://104.20.20.20 -H "host:www.9sep.org"
指定IP查看HTTPS请求过程以及结构:
curl --resolve "www.9sep.org:443:104.20.20.20" -svo /dev/null https://www.9sep.org/

2,IPv4地址有限,现有基础云设施可以快速扫描IPv4全网:在全球互联计算机网络中,IPv4的IP总数量是多少?答案是:2^32 = 4294967296 个,目前我们在阿某/腾某/某某/某某某云上租带宽充裕的按需付费型VPS过滤掉常见CDN IP段后扫描IPv4全网大概只需要4个半小时左右完成(实测为:单机UDP扫IPv4全网NTP 123端口只花了4个半小时,流量花费大概3-400G左右具体忘记了,大佬赞助的临时机器也不在意这些,如果扫IPv4全网TCP你可能需要多来几台机器以达到此速度,以上数据仅供参考,实际钞能力只会更快)

3,源站配置SSL证书必然包含具体域名信息

综合上述条件,已知目标域名我们有以下办法找到域名对应源站服务器IP:

a,带着目标域名HOST头逐一去遍历有限IPv4网络空间
b,扫描IPv4全网IP的HTTPS端口(默认为:443)并解析读取SSL证书信息判断是否包含目标域名

知道了办法动手自己玩玩?专门租服务器干这个活有点临时抱佛脚的意思,网上现成有 censys.io/shodan.io/fofa.so 等互联网络空间测绘服务商分布式24小时不间断扫描IPv4全网并记录已知特征信息,对外提供了检测服务,并且目前大部分都有开放免费使用,这里以 censys 为例我们尝试找一下隐藏在CDN后的源站IP:

IPv4全网查找IP域名匹配:https://censys.io/ipv4?q=www.9sep.org
IPv4全网查找IP域名SSL证书:https://censys.io/certificates?q=www.9sep.org

censys的数据有新有旧,使用Curl命令可以快速甑别和验证

如何防止入站扫描找到隐藏在CDN后的源站IP?

说的挺恐怖,那接入Cloudflare等提供高防CDN服务的网络不是也没啥防护作用了?有道是:办法总比问题多,这里以Cloudflare CDN为例通过BASH SHELL脚本配置Linux系统防火墙白名单规则:限制所有入站访问,入站访问仅向特定IP段特定协议以及端口开放:对CDN IP段开放正常回源访问,快速简单粗暴直接且有效的解决方案代码实现如下:

#!/bin/bash
# Name  : Anti IP Leakage
# Author: Zhys
# Date  : 2019

# 禁止来自IPv4的所有HTTP/S访问请求
iptables -I INPUT -p tcp --dport 80 -j DROP
iptables -I INPUT -p tcp --dport 443 -j DROP

# 对Cloudflare CDN IPv4地址开放HTTP/S入站访问
for i in `curl https://www.cloudflare.com/ips-v4`; do iptables -I INPUT -s $i -p tcp --dport 80 -j ACCEPT; done
for i in `curl https://www.cloudflare.com/ips-v4`; do iptables -I INPUT -s $i -p tcp --dport 443 -j ACCEPT; done

# 禁止来自IPv6的所有HTTP/S访问请求
ip6tables -I INPUT -p tcp --dport 80 -j DROP
ip6tables -I INPUT -p tcp --dport 443 -j DROP

# 对Cloudflare CDN IPv6地址开放HTTP/S入站访问
for i in `curl https://www.cloudflare.com/ips-v6`; do ip6tables -I INPUT -s $i -p tcp --dport 80 -j ACCEPT; done
for i in `curl https://www.cloudflare.com/ips-v6`; do ip6tables -I INPUT -s $i -p tcp --dport 443 -j ACCEPT; done

# 保存iptables配置
iptables-save
ip6tables-save

# 注意:80/443为默认HTTP/S协议通讯使用端口,若实际应用有使用非80/443端口进行,请依葫芦画瓢自行修改脚本
# Ubuntu系统可以使用UFW则类似:for i in `curl https://www.cloudflare.com/ips-v4`; do ufw allow proto tcp from $i to any port 80; done
# 基于Linux系统兼容性考虑脚本使用iptables配置系统防火墙,请自行根据各自系统、防火墙不同做相应配置调整实施

Bash化简

#!/bin/bash
# Name  : Anti IP Leakage
# Author: Zhys
# Date  : 2019

# 禁止来自IPv4的所有HTTP/S访问请求
iptables -I INPUT -p tcp -m multiport --dports 80,443 -j DROP

# 对Cloudflare CDN IPv4地址开放HTTP/S入站访问
for i in `curl https://www.cloudflare.com/ips-v4`; do iptables -I INPUT -s $i -p tcp -m multiport --dport 80,443 -j ACCEPT; done

# 禁止来自IPv6的所有HTTP/S访问请求
ip6tables -I INPUT -p tcp -m multiport --dports 80,443 -j DROP

# 对Cloudflare CDN IPv6地址开放HTTP/S入站访问
for i in `curl https://www.cloudflare.com/ips-v6`; do ip6tables -I INPUT -s $i -p tcp -m multiport --dport 80,443 -j ACCEPT; done

# 保存iptables配置(请确保命令正确配置再保存)
iptables-save
ip6tables-save

快速验证防火墙配置是否正确、有效
查看当前iptables规则集:
iptables -L
ip6tables -L
本地直接访问源站应该返回失败:
curl -svo /dev/null http://源站IP -H "host:域名"
对比本地通过Cloudflare CDN正常访问:
curl -svo /dev/null http://104.20.0.0 -H "host:域名"
验证HTTPS请求则:
curl --resolve "www.9sep.org:443:源站IP" -svo /dev/null https://www.9sep.org/
以上不做详解,自行搜索查阅curl相关文档
附上Cloudflare CDN网络工作IP段:https://www.cloudflare.com/ips/

再次提醒注意:最佳规则配置应在入站防火墙上,使用iptables是因为它的兼容性适用几乎所有Linux系统,实际各大主流云厂商(GCP/AWS/AZ/阿某云/腾某云等)默认都会有入站防火墙机制(操作放行网络端口的地方);其次注意规则匹配优先级(顺序)问题

出站访问泄露源站IP

这个问题很宽泛原因可能是多方面的,理论上所有出站请求都必然存在泄露源站IP的风险,这里列举几个常见方面:
1,源站 IP 是否在一些无法或不方便接入CDN的服务中泄露,如自建邮件服务器的 MX 记录、bbs记录等
2,是否存在网站源码信息泄露,如 phpinfo() 指令、301/302跳转中会包含有域名标识、服务器IP地址
3,源站服务器中是否存在木马、后门之类的安全隐患
4,网站所使用程序是否存在已知安全漏洞被渗透利用
5,源站上特定已知且可控的服务:源站上直接进行采集操作(被目标站长反打了一顿)、某些面板通过Nginx错配了SSL证书以及301跳转、各种论坛/博客发送注册/找回密码的邮件服务、WordPress博客的留言回复通知等(主要/常见的出站请求泄露源站服务器IP问题点)

如何防止出站请求泄露源站IP?

解决问题的原则:
木桶效应:一只水桶能装多少水取决于它最短的那块木板,最弱的环节决定总体安全水平
奥卡姆剃刀:如无必要,勿增实体
了解你的业务:关闭不必要对外端口/应用/服务
复杂问题简单化:所有涉及请求出站的应用服务能拆分拆分,不能拆分的想办法中转隔离
1,对于用户已知且可控的服务:不要在源站上直接对外进行操作(比如:远程SMTP发信),拆分它或者尝试使用公共服务
2,不要把内部用途的应用或服务端口暴露在公网:phpMyAdmin、数据库(MySQL/Memcache/PostgreSQL/Redis等)
3,及时更新漏洞(系统的、程序的)修复,不要使用弱密码

防止出站请求泄露源站IP的方方面面很烦杂,个中关键是在于对自己服务的了解:系统的/网站程序的/业务的各个环节了解,具体问题具体分析同时也要一分为二看问题,需要多一点反向思维

域名历史解析记录泄露源站IP

原因:互联网中有很多的DNS/域名IP查询服务商会进行DNS解析结果缓存,一些服务商甚至号称:数据记录,永久存储,通过它们可以查询到域名的历史解析数据,通过curl命令可以很快的确认是否源站依旧在历史DNS解析IP上
解决办法:关键是对外解除与域名的关联,检查当前的 DNS 解析配置,查看是否还存在解析到源站 IP 的记录;更换服务器IP以解除原始IP与域名的关联,当然如果你能确保域名与域名之间别人找不到关联也可以换个域名继续源站玩

关于源站IP泄露问题,本文主要提供常见问题解决思路和方向,像CDN账号使用弱密码被人爆破然后直接拿到源站服务器地址这类的;言之不尽,言尽于此,如果你有疑问或者建议请在下方留言回复互相查漏补缺

comment-author avatars

Zhys

Cherish the time! Don't waste even nine seconds to remember the past, live in the present and for the future planning.

猜你喜欢...

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注

邮件通知