必须用virtualhost内rewritecond+rewriterule或容器拦截非法host头:只允许白名单域名(如www.yourdomain.com),其余一律403拒绝,并清除x-forwarded-host等高危代理头。

直接通过主机名(比如 http://evil-scanner.net 或伪造的 Host: scanbot.example.org)访问你的 Apache 服务器,本质是 Host 头被恶意利用——它绕过了域名白名单,触发了默认虚拟主机或错误路由。这不是 IP 访问问题,而是虚拟主机层面的 Host 头校验缺失。拦截关键在于:**只允许已知合法主机名,其余一律 403 拒绝**,且必须在 VirtualHost 内完成,不依赖后端代码。
用 RewriteCond + RewriteRule 精准拦截非法 Host 头
这是最直接、兼容性好、支持正则和大小写的方案,适用于所有 Apache 2.4+ 环境:
- 确保
RewriteEngine On已启用 - 在你要保护的
<virtualhost></virtualhost>或<virtualhost></virtualhost>块内添加以下规则 - 匹配逻辑:只要
%{HTTP_HOST}不在白名单中,就返回 403
示例配置:
RewriteEngine On
RewriteCond %{HTTP_HOST} !^(www\.yourdomain\.com|yourdomain\.com|localhost|127\.0\.0\.1)$ [NC]
RewriteRule ^ - [F]
说明:[NC] 忽略大小写;^ - [F] 表示匹配即返回 403,不重写路径;正则中用 \. 转义点号,避免误匹配。
用 容器做更清晰的白名单控制(Apache 2.4.8+)
比 Rewrite 更语义化,逻辑更直观,适合多域名或需分环境管理的场景:
PHP中文网提供Apache 2.4.62 官方 tar.gz 源码包下载,通过源码编译安装,开发者能够灵活定制模块、优化性能并精准控制安装路径,满足多样化的业务需求。
- 把合法主机名写进变量或直接判断
- 用
<if></if>判断 Host 是否不在白名单内 - 命中即拒绝,且可配合自定义错误页
示例:
<if>
Require all denied
</if>
注意:Require all denied 在 VirtualHost 内有效,无需额外 Directory 块;i 标志等效于 [NC],忽略大小写。
补充防御:防止 Host 头绕过与协议降级
单靠 Host 匹配还不够。攻击者可能伪造 X-Forwarded-Host、使用 HTTP/HTTPS 混合请求,或利用空 Host 头试探:
- 显式清除高危代理头:
RequestHeader unset X-Forwarded-Host和RequestHeader unset X-Original-Host - 放行空 Referer 和空 Host(某些合法请求会这样),但 Host 为空时不应放行非法访问,建议保留默认拒绝逻辑
- 若站点强制 HTTPS,务必开启 HSTS:
Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains",防止首次 HTTP 请求被劫持并注入恶意 Host
验证是否生效的简单方法
不用重启 Apache,改完配置后立即测试:
- 用 curl 模拟非法 Host:
curl -H "Host: bad-domain.com" http://your-server-ip/,应返回 403 - 用合法域名访问:
curl -H "Host: www.yourdomain.com" http://your-server-ip/,应正常响应 - 检查 Apache 错误日志:
tail -f /var/log/apache2/error.log,确认有client denied by server configuration类提示










