nginx deny限制路径绕过
简介
这篇文章中,分享一个技巧。解析问题来绕过路由限制
环境记录
采取docker-compose 部署
mkdir nginx_test
cd nginx_test
touch docker-compose.yml
mkdir -p nginx/conf.d
touch nginx/conf.d/default.conf
version: '3'
services:
nginx:
image: nginx:latest
ports:
- "80:80"
volumes:
- ./nginx/conf.d:/etc/nginx/conf.d
- ./html:/usr/share/nginx/html
server {
listen 80;
server_name localhost;
location / {
root /usr/share/nginx/html;
index index.html index.htm;
}
}
从nginx解析问题开始
Nginx
是一个高性能的 HTTP
服务器和反向代理服务器,广泛应用于网站托管和负载均衡。解析问题通常指Nginx
在处理客户端请求时遇到的各种安全问题
Missing root location
server {
root /etc/nginx;
location /hello.txt {
try_files $uri $uri/ =404;
proxy_pass http://127.0.0.1:8080/;
}
}
如上,这个nginx配置例子,/etc/nginx
被指定为根目录。此设置允许访问指定根目录中的文件,例如 /hello.txt
。但是,配置中并没有根位置 ( location / {...}
) 的配置。意味着 root 指令全局适用,允许对根路径 /
的请求访问 /etc/nginx
下的文件,攻击者可通过提供位于 /etc/nginx/nginx.conf
的 Nginx
配置文件来暴露敏感信息
攻击举例:



Alias LFI Misconfiguration
在Nginx
的配置文件中,存在一类本地文件包含 (LFI) 的漏洞,如下demo配置:
location /imgs {
alias /path/images/;
}
location /imgs/ {
alias /path/images/;
}
Unsafe path restriction 限制路径绕过
本文主要分享如下配置的绕过
location = /admin {
deny all;
}
location = /admin/ {
deny all;
}


trim方法
在编程中,trim
函数用于去除字符串两端的空白字符(例如空格、制表符、换行符等)是一个常用的字符串操作,对于清理和规范化输入数据非常有用。不同编程语言的 trim
函数可能名称略有不同,但功能基本相同。下面介绍常见编程语言中 trim
函数的使用示例
Python 中的 strip
方法用于去除字符串两端的空白字符。
text = " Hello, World! "
trimmed_text = text.strip()
print(trimmed_text) # 输出: "Hello, World!"
JavaScript 中的 trim
方法用于去除字符串两端的空白字符。
let text = " Hello, World! ";
let trimmedText = text.trim();
console.log(trimmedText); // 输出: "Hello, World!"
Java 中的 trim
方法用于去除字符串两端的空白字符。
public class Main {
public static void main(String[] args) {
String text = " Hello, World! ";
String trimmedText = text.trim();
System.out.println(trimmedText); // 输出: "Hello, World!"
}
}
C# 中的 Trim
方法用于去除字符串两端的空白字符。
using System;
class Program {
static void Main() {
string text = " Hello, World! ";
string trimmedText = text.Trim();
Console.WriteLine(trimmedText); // 输出: "Hello, World!"
}
}
PHP 中的 trim
函数用于去除字符串两端的空白字符。
$text = " Hello, World! ";
$trimmed_text = trim($text);
echo $trimmed_text; // 输出: "Hello, World!"
?>
Ruby 中的 strip
方法用于去除字符串两端的空白字符。
text = " Hello, World! "
trimmed_text = text.strip
puts trimmed_text # 输出: "Hello, World!"
Go 语言中没有内置的 trim
方法,但可以使用 strings
包中的 TrimSpace
函数。
package main
import (
"fmt"
"strings"
)
func main() {
text := " Hello, World! "
trimmedText := strings.TrimSpace(text)
fmt.Println(trimmedText) // 输出: "Hello, World!"
}
在 SQL 中,可以使用 TRIM
函数去除字符串两端的空白字符。
SELECT TRIM(' Hello, World! ') AS trimmed_text;
本文主要介绍python 和 nodejs作为后台此类问题绕过情况
s = "\xa0 laotie233 \x85"
print(bytes(s.encode()))
print(bytes(s.strip().encode()))

s = "\xa0 laotie233 \x85"
s.trim()

nodejs绕过
const express = require('express');
const app = express();
const port = 3000;
// 中间件示例:记录请求日志
app.use((req, res, next) => {
console.log(`${req.method} ${req.url}`);
next();
});
// 中间件示例:解析 JSON 请求体
app.use(express.json());
// /admin 路由
app.get('/admin', (req, res) => {
return res.send('ADMIN');
});
// 404 错误处理
app.use((req, res, next) => {
res.status(404).send('404 Not Found');
});
// 全局错误处理
app.use((err, req, res, next) => {
console.error(err.stack);
res.status(500).send('Something broke!');
});
app.listen(port, '0.0.0.0', () => {
console.log(`Server is running on http://0.0.0.0:${port}`);
});

server {
listen 80;
server_name localhost;
location = /admin {
deny all;
}
location = /admin/ {
deny all;
}
# location / {
# root /usr/share/nginx/html;
# index index.html index.htm;
# }
location / {
proxy_pass http://192.168.56.130:3000;
}
}



python类后台绕过


server {
listen 80;
server_name localhost;
location = /admin {
deny all;
}
location = /admin/ {
deny all;
}
# location / {
# root /usr/share/nginx/html;
# index index.html index.htm;
# }
location / {
proxy_pass http://192.168.56.130:8000;
}
}



修复方式
location ~* ^/admin {
deny all;
}
server {
listen 80;
server_name localhost;
location ~* ^/admin {
deny all;
}
location ~* ^/admin/ {
deny all;
}
# location / {
# root /usr/share/nginx/html;
# index index.html index.htm;
# }
location / {
proxy_pass http://192.168.56.130:8000;
}
}

写在最后
本文介绍的只是一些初步的相关知识,后续应该会继续写较为深入的版本
参考
https://github.com/detectify/vulnerable-nginx
https://rafa.hashnode.dev/exploiting-http-parsers-inconsistencies
声明:⽂中所涉及的技术、思路和⼯具仅供以安全为⽬的的学习交流使⽤,任何⼈不得将其⽤于⾮法⽤途以及盈利等⽬的,否则后果⾃⾏承担。所有渗透都需获取授权!
如果你是一个网络安全爱好者,欢迎加入我的知识星球:zk安全知识星球,我们一起进步一起学习。星球不定期会分享一些前言漏洞,每周安全面试经验、SRC实战纪实等文章分享,微信识别二维码,只需25,即可加入,如不满意,72 小时内可在 App 内无条件自助退款。

