type
Post
status
Published
slug
2022/12/26/use-coredns-defense-against-DNS-pollution
summary
使用 CoreDNS 对抗 DNS 污染
tags
coredns
工具
Linux
category
技术分享
icon
password
Property
Dec 26, 2022 09:39 AM
created days
家里面的宽带是移动的宽带、最近发现DNS污染日异严重,甚至刷抖音、家里孩子上网课都受到了影响。在更换为阿里 DNS 之后,仍然没见改善,于是就准备在内网自建 DNS 从而对抗运营商的 DNS 污染。

CoreDNS

CoreDNS 是一个 DNS 服务器。它是用 Go 编写的。由于其灵活性,它可以在多种环境中使用。 CoreDNS 在 Apache License Version 2 下获得许可,并且完全开源。
同时大名鼎鼎的k8s使用CoreDNS进行服务发现。稳定性以及其功能的强大毋庸置疑。CoreDNS基本沿用了Caddy的插件架构,所以CoreDNS的配置文件的语法跟Caddy的配置文件语法相同。

CoreDNS 配置文件

一个最简单的配置文件可以是这样:
.:53{ forward . 8.8.8.8 log health }
将配置保存为文件Corefile,运行命令sudo coredns -conf Corefile,即可在本地同时监听TCP和UDP 53端口,将所有UDP查询请求转发到8.8.8.8再返回,可以通过dig @::1 -p 53 twitter.com进行测试。
但是这个配置文件在国内几乎是没啥用的,原因自然是8.8.8.8乃国内重点关注对象,直接访问得到的结果都是二手信息。一个好一点的方案是使用非标准端口,比如:
.:53{ forward . 208.67.222.222:443 log health }
forward插件支持多个上游服务器以实现简单的负载均衡:
.:53{ forward . 208.67.222.222:443 208.67.222.222:5353 208.67.220.220:443 208.67.220.220:5353 log health }
大陆的网络环境非常复杂,UDP非标准端口也只在某些地区某些运营商有用,现在比较好的一个选择是DoT,即DNS over TLS,知名的支持DoT的公共DNS服务有Quad9的9.9.9.9,Google的8.8.8.8以及Cloudflare的1.1.1.1,可以这么使用:
.:53{ forward . 127.0.0.1:5301 127.0.0.1:5302 127.0.0.1:5303 log health } .:5301 { forward . tls://9.9.9.9 { tls_servername dns.quad9.net } cache } .:5302 { forward . tls://1.1.1.1 tls://1.0.0.1 { tls_servername 1dot1dot1dot1.cloudflare-dns.com } cache } .:5303 { forward . tls://8.8.8.8 tls://8.8.4.4 { tls_servername dns.google } cache }
这样除了国内把连接reset,基本可以得到正确的DNS解析结果。
另一个问题是国内CDN友好,常用做法是使用 FelixOnMars的大陆区域名列表过滤。这个列表是给dnsmasq 用的,经过转换可以给CoreDNS用,为了实现分流解析,可以将所有请求都通过forward转发到无污染上游解析,将大陆区域名列表加到异常列表,再把剩下的所有请求(其实就是异常列表中的域名)通过下一条链的 forward 转发到国内(最好是当前ISP的)DNS server,比如:
.:53{ forward . 127.0.0.1:5301 127.0.0.1:5302 127.0.0.1:5303 { except www.taobao.com } forward . 116.228.111.118 180.168.255.18 log health } .:5301 { forward . tls://9.9.9.9 { tls_servername dns.quad9.net } cache } .:5302 { forward . tls://1.1.1.1 tls://1.0.0.1 { tls_servername 1dot1dot1dot1.cloudflare-dns.com } cache } .:5303 { forward . tls://8.8.8.8 tls://8.8.4.4 { tls_servername dns.google } cache }
这里except www.taobao.com表示www.taobao.com这个域名不要通过forward解析,后面可以跟多个域名,于是这些域名会掉到下面的forward插件进行解析,而116.228.111.118180.168.255.18则是我的ISP提供的DNS服务器,可以得到最好的CDN友好的结果。
这时就可以用上FelixOnMars的大陆区域名列表了,用以下命令可以得到所有域名连接而成的长字符串,放在except标识符后面:
china=`curl https://fastly.jsdelivr.net/gh/felixonmars/dnsmasq-china-list/accelerated-domains.china.conf -s | while read line; do awk -F '/' '{print $2}' | grep -v '#' ; done | paste -sd " " -` echo " except $china " >> Corefile
FelixOnMars同时还提供了Google和Apple的域名列表,这在某些地区某些ISP可以得到国内镜像的IP,所以最后可以写一个这样的shell脚本用于生成Corefile:
#!/bin/sh echo 'use "curl -sSL git.io/corefile | bash" to update Corefile' echo "remember to change 192.168.1.1 to your ISP's DNS server address or use public DNS server such as 114/DNSPod etc. directly" china=`curl -sSL https://github.com/felixonmars/dnsmasq-china-list/raw/master/accelerated-domains.china.conf | while read line; do awk -F '/' '{print $2}' | grep -v '#' ; done | paste -sd " " -` apple=`curl -sSL https://github.com/felixonmars/dnsmasq-china-list/raw/master/apple.china.conf | while read line; do awk -F '/' '{print $2}' | grep -v '#' ; done | paste -sd " " -` google=`curl -sSL https://github.com/felixonmars/dnsmasq-china-list/raw/master/google.china.conf | while read line; do awk -F '/' '{print $2}' | grep -v '#' ; done | paste -sd " " -` cat>Corefile<<EOF . { # uncomment below lines to enable ads plugin #ads { # default-lists # blacklist https://raw.githubusercontent.com/privacy-protection-tools/anti-AD/master/anti-ad-domains.txt # whitelist https://files.krnl.eu/whitelist.txt # log # auto-update-interval 24h # list-store ads-cache #} hosts { fallthrough } # choose your favourite DNS servers below forward . 127.0.0.1:5300 127.0.0.1:5301 127.0.0.1:5302 127.0.0.1:5303 127.0.0.1:5304 { except $china $apple $google dns.quad9.net cloudflare-dns.com dns.google dns.opendns.com } forward . 192.168.1.1 log cache # uncomment lines below to enable redis plugin #redisc { # endpoint 127.0.0.1:6379 #} health reload } .:5300 { bind 127.0.0.1 forward . tls://208.67.222.222 tls://208.67.220.220 { tls_servername dns.opendns.com health_check 60s } cache } .:5301 { bind 127.0.0.1 forward . tls://9.9.9.9 tls://9.9.9.10 { tls_servername dns.quad9.net health_check 60s } cache } .:5302 { bind 127.0.0.1 forward . tls://1.1.1.1 tls://1.0.0.1 { tls_servername cloudflare-dns.com health_check 60s } cache } .:5303 { bind 127.0.0.1 forward . tls://8.8.8.8 tls://8.8.4.4 { tls_servername dns.google health_check 60s } cache } EOF

CoreDNS systemd 文件

sudo vim /etc/systemd/system/coredns.service
[Unit] Description=Coredns server daemon Documentation=coredns After=network.target [Service] EnvironmentFile= ExecStart=/usr/sbin/coredns -conf=/etc/coredns/Corefile --log_dir=/var/log/coredns/coredns.log ExecReload=/bin/kill -HUP $MAINPID Type=simple KillMode=process Restart=on-failure RestartSec=42s [Install] WantedBy=multi-user.target
sudo systemctl daemon-reload sudo systemctl enable coredns.service --now

参考资料

CoreDNS搭建无污染DNS
我之前整理过在国内搭建无污染DNS的 一些方法,github上各种轮子也层出不穷,但基本原理几乎不变。自从半年多前开始用 CoreDNS,我觉得可以不用dnsmasq/ overture/chinadns这些轮子了,CoreDNS完全符合我的需求: CoreDNS的来头不小,它的 作者是最好的开源 DNS package的作者,CoreDNS底层也使用了这个package。大名鼎鼎的k8s使用CoreDNS进行服务发现。CoreDNS基本沿用了 Caddy 的插件架构,所以CoreDNS的配置文件的语法跟Caddy的配置文件语法相同。 一个最简单的配置文件可以是这样: 将配置保存为文件 Corefile,运行命令 sudo coredns -conf Corefile,即可在本地同时监听TCP和UDP 53端口,将所有UDP查询请求转发到 8.8.8.8再返回,可以通过 dig @::1 -p 53 twitter.com 进行测试。 但是这个配置文件在国内几乎是没啥用的,原因自然是 8.8.8.8 乃老大哥重点关注对象,直接访问得到的结果都是二手信息。一个好一点的方案是使用非标准端口,比如: forward 插件支持多个上游服务器以实现简单的负载均衡: 大陆的网络环境非常复杂,UDP非标准端口也只在某些地区某些运营商有用,现在比较好的一个选择是DoT,即DNS over TLS,知名的支持DoT的公共DNS服务有Quad9的 9.9.9.9,Google的 8.8.8.8以及Cloudflare的 1.1.1.1 ,可以这么使用: 这样除了老大哥把连接reset,基本可以得到正确的DNS解析结果。 另一个问题是国内CDN友好,我一直以来的做法是使用 FelixOnMars的大陆区域名列表过滤。这个列表是给dnsmasq用的,经过转换可以给CoreDNS用,这利用了CoreDNS的两个插件来实现,分别是 forward和 proxy,这两个插件的功能非常相似,都是将DNS解析请求发给上游DNS server,再将结果取回返回给客户端。为了实现分流解析,可以将所有请求都通过 forward转发到无污染上游解析,将大陆区域名列表加到异常列表,再把剩下的所有请求(其实就是异常列表中的域名)通过 proxy 转发到国内(最好是当前ISP的)DNS server,比如: 这里 except www.taobao.com表示
CoreDNS搭建无污染DNS
💡
注意:此文章里面提供的 proxy 与 block 插件、官方已经弃用、无法正常完成编译。
 
欢迎加入喵星计算机技术研究院,原创技术文章第一时间推送。
notion image
 
BPF 学习系列之 - 用户空间探针 - uprobes 与 uretprobes 使用 systemd 开机挂载其它硬盘

  • Waline
  • Utterance