分享

Hijack DnsPod HttpDNS | @sskaje

 xxqa的新文艺 2019-08-16
劫持DNS是个很简单的工作,家用路由器基本都自带dnsmasq,直接加解析就行。

之前某次尝试劫持某视频App的广告接口解析到一个空的本地服务器上,发现该App使用了DnsPod的HttpDNS服务,所以传统的DNS劫持方案不好用。而EdgeRouter的DPI功能也没有对外开放墙一般的高级接口,所以这次用NAT来实现。

首先,原有的App广告流程如下:

图中的流程很传统,12为HttpDNS请求过程,34为广告资源拉取。没有画路由器,因为这里没有用到路由器的DNS转发功能,所以路由器不重要。

针对这个场景,如果想劫持HttpDNS Server的解析,就需要在终端和HttpDNS Server之间加上一个代理,图就变成了:

这里Hijack Server存在的前提是使用了非ssl/tls的传输协议。在HttpDNS的常规逻辑上,也不太好加常用的SSL,因为不会有CA给IP颁发证书。DnsPod的HttpDNS的一个参考地址是 http://119.29.29.29/d?dn= 。当然企业级自己预置证书这种玩法我就管不了了。应该不会有人问为什么HttpDNS不用域名来设置目标服务器地址吧。

从实际角度来说,图应该变成下边这个样子,我没有刻意地画路由、防火墙设备,只是拿个方框区分出所谓的LAN和WAN。

又回到常识性的逻辑上,1/4这个链路其实是不可能成立的,因为App这边的IP是写死的。在不修改App的前提下,图其实应该是这样的:

从路由/防火墙上配置规则,将App的HttpDNS Server的请求,转发到Hijack Server上。

所以在EdgeRouter上,我们要做的第一件事情是,DNAT。我的Hijack Server IP是192.168.1.13,路由器IP是192.168.1.1,待劫持的设备IP是192.168.1.151。我定义了两个组,一个是DnsPod HttpDNS的所有IP,一个是需要劫持的LAN IP。所以参考的配置如下。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
[edit]
root@ubnt# show firewall group address-group DNSPOD_HTTPDNS_SERVER
address 182.254.118.118
address 182.254.116.116
address 119.28.28.28
address 119.29.29.29
[edit]
root@ubnt# show firewall group address-group SRC_HIJACK_DNSPOD_HTTPDNS
address 192.168.1.151
[edit]
root@ubnt# show service nat rule 4108
description "hijack dnspod http dns"
destination {
     group {
         address-group DNSPOD_HTTPDNS_SERVER
     }
     port 80
}
inbound-interface eth0
inside-address {
     address 192.168.1.1
     port 80
}
log disable
protocol tcp
source {
     group {
         address-group SRC_HIJACK_DNSPOD_HTTPDNS
     }
}
type destination

不出意料的,挂了。请求发出去一致没有响应,开日志发现,只有SYN包到了192.168.1.13上。原因是:在LAN里直接做DNAT,只是修改了目的地址,源地址没改,导致在同一个局域网下,1.13这台机器看到源IP是同网段,所以把ACK直接发给了源IP的机器,于是出现了下图:

解决方案就是再开一个MASQUERADE。配置如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
root@ubnt# show service nat rule 5108
description "hijack dnspod http dns"
destination {
     address 192.168.1.13
     port 80
}
log disable
outbound-interface eth0
protocol tcp
source {
     group {
         address-group SRC_HIJACK_DNSPOD_HTTPDNS
     }
}
type masquerade

1.13上,我用php写了一个简单的HttpDNS查询接口,预留了一个读配置文件的地方:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
<?php
$upstream = [
        '182.254.118.118',
        '182.254.116.116',
        '119.28.28.28',
        '119.29.29.29',
];
$hijack = include(__DIR__ . '/hijack_config.php');
if (isset($hijack[$_GET['dn']])) {
$result = $hijack[$_GET['dn']];
if (!empty($_GET['ttl'])) {
$result .= ',3600';
}
echo $result;
exit;
}
$url = 'http://' . $upstream[array_rand($upstream)] . '/d?dn=' . $_GET['dn'];
if (!empty($_GET['ttl'])) {
$url .= '&ttl=' . $_GET['ttl'];
}      
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_URL, $url);
echo curl_exec($ch);
curl_close($ch);
exit;

配置文件就是同目录下的 hijack_config.php,内容如下

1
2
3
4
<?php
return [
  'aaa.bbb.com' => '192.168.1.13',
];

nginx配置也很简单

1
2
3
4
5
6
7
8
9
server {
listen 80 default_server;
root /opt/deploy/dnspod-httpdns;
rewrite ^/d$ /proxy.php break;
        location ~ \.php$ {
                include fastcgi-php.conf;
                fastcgi_pass unix:/tmp/php-fpm.sock;
        }
}


Hijack DnsPod HttpDNS by @sskaje: https:///2019/04/hijack-dnspod-httpdns/

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多