透明代理中iptables设置

关键点说明:

  • 透明代理端口 : tport=3333,这里使用Clash的redir-port参数值
  • 无污染的DNS服务转发端口: dns_port=1053,这里使用Clash的dns.listen参数值
  • iptables命令: 内网消息转发规则配置
  • dnsmasq: 内置DNS服务

透明代理配置方法有:

  • 简单粗暴: 所有HTTP(S)请求都转发给透明代理端口处理,由透明代理决定是否使用代理转发。
  • 精细化分: 根据ipset规则识别流量是否需要转发给透明代理端口,减少透明代理处理的消息量(透明代理出问题也不会影响直连的网站)。

方法一:所有流量都转发给透明代理处理

这种方法适合这样的场景:

  1. 透明代理具备规则转发功能,可以根据URL规则或IP规则判断是否使用代理。
  2. 透明代理处理能力还不错,对于家庭内部流量足够支撑情况下,Clash通常足够。

详细的配置iptables规则如下:

# 添加iptables规则
table_name="CLASH_RULES"
lan_ipaddr=$(nvram get lan_ipaddr)      # 局域网地址
redir_port=3333                         # 透明代理端口
dns_port=1053                           # 无污染的DNS服务端口(Clash内置DNS服务或者其他安全DNS服务)

iptables -t nat -N ${table_name}
iptables -t nat -F ${table_name}
# Fake-IP 规则添加
iptables -t nat -A OUTPUT -p tcp -d 198.18.0.0/16 -j REDIRECT --to-port ${redir_port}
iptables -t nat -A PREROUTING -p tcp -s ${lan_ipaddr}/16 -j ${table_name}
# 本地地址请求不转发
iptables -t nat -A ${table_name} -d 10.0.0.0/8 -j RETURN
iptables -t nat -A ${table_name} -d 127.0.0.0/8 -j RETURN
iptables -t nat -A ${table_name} -d 169.254.0.0/16 -j RETURN
iptables -t nat -A ${table_name} -d 172.16.0.0/12 -j RETURN
iptables -t nat -A ${table_name} -d ${lan_ipaddr}/16 -j RETURN
# 服务端口${redir_port}接管HTTP/HTTPS请求转发, 过滤 22,1080,8080一些代理常用端口
iptables -t nat -A ${table_name} -s ${lan_ipaddr}/16 -p tcp -m multiport --dport 80,443 -j REDIRECT --to-ports ${redir_port}

# 转发DNS请求到端口 dns_port 解析
iptables -t nat -N ${table_name}_DNS
iptables -t nat -F ${table_name}_DNS
iptables -t nat -A ${table_name}_DNS -p udp -s ${lan_ipaddr}/16 --dport 53 -j REDIRECT --to-ports $dns_port
iptables -t nat -I OUTPUT -p udp --dport 53 -j ${table_name}_DNS
iptables -t nat -A PREROUTING -p udp -s ${lan_ipaddr}/16 --dport 53 -j ${table_name}_DNS


# 清理iptables规则
table_name="CLASH_RULES"
lan_ipaddr=$(nvram get lan_ipaddr)      # 局域网地址
redir_port=3333                         # 透明代理端口
# Fake-IP 规则清理
iptables -t nat -D OUTPUT -p tcp -d 198.18.0.0/16 -j REDIRECT --to-port ${redir_port}
iptables -t nat -D PREROUTING -p tcp -s ${lan_ipaddr}/16 -j ${table_name}
iptables -t nat -F ${table_name}
iptables -t nat -X ${table_name}

iptables -t nat -D PREROUTING -p udp -s ${lan_ipaddr}/16 --dport 53 -j ${table_name}_DNS
iptables -t nat -D OUTPUT -p udp --dport 53 -j ${table_name}_DNS
iptables -t nat -F ${table_name}_DNS
iptables -t nat -X ${table_name}_DNS

方法二:精细化分流量后转发给透明代理处理

这种方法适合这样的场景:

  1. 透明代理不具备规则转发功能,不能根据URL规则或IP规则判断是否使用代理。
  2. 内网的流量很大,而透明代理处理能力不足时。
  • ipset配置过程如下:
# 创建ipset黑名单(命中规则走代理)
ipset -! create gfwlist nethash && ipset flush gfwlist

# /jffs/configs/dnsmasq.d
conf_dir=`awk -F'=' '/conf-dir/{ print $2 }' dnsmasq.conf`
echo "配置ipset规则目录: ${conf_dir}"

# 添加Ipset规则到 dnsmasq 服务中(只要ipset表创建正确dnsmasq就会更新对应的数据)
cd ${conf_dir} && ln -sf /koolshare/clash/gfwlist.conf gfwlist.conf && ln -sf /koolshare/clash/wblist.conf wblist.conf

# 重启dnsmasq
service restart_dnsmasq

其中,gfwlist.conf文件下载地址在这里

  • iptables配置过程(添加、删除规则操作)如下:
# 添加iptables规则
table_name="CLASH_RULES"
lan_ipaddr=$(nvram get lan_ipaddr)      # 局域网地址
redir_port=3333                         # 透明代理端口
iptables -t nat -N ${table_name}
iptables -t nat -F ${table_name}
iptables -t nat -A PREROUTING -p tcp -s ${lan_ipaddr}/16 -m set --match-set gfwlist dst -j ${table_name}
# 使用 ipset 规则转发处理请求
iptables -t nat -A ${table_name} -p tcp -m set --match-set gfwlist dst -j REDIRECT --to-ports ${redir_port}

# 清理iptables规则
table_name="CLASH_RULES"
lan_ipaddr=$(nvram get lan_ipaddr)      # 局域网地址
redir_port=3333                         # 透明代理端口

iptables -t nat -D PREROUTING -p tcp -s ${lan_ipaddr}/16 -m set --match-set gfwlist dst -j ${table_name}
iptables -t nat -D ${table_name} -p tcp -m set --match-set gfwlist dst -j REDIRECT --to-ports ${redir_port}
iptables -t nat -F ${table_name}
iptables -t nat -X ${table_name}

最后

两种方法可以看出,第二种方法更通用一些,比如启动一个ss/ssr/v2ray代理,通过方法二就可以实现透明代理功能。

而第一种方法就不那么通用,更适合使用Clash来实现透明代理功能。