我们有许多用于转发连接的iptables规则,这些规则是可靠且运行良好的 .
例如,端口80转发到同一台机器(网络服务器)上的端口8080 . 当给定的Web服务器重新启动时,我们将请求转发到端口8080上的另一个IP,该端口显示维护页面 . 在大多数情况下,此其他IP位于单独的服务器上 .
这一切都完美无缺,直到我们安装了bridge-utils并改为使用桥接器br0而不是eth0作为接口 .
我们转换为使用网桥接口的原因是为了获得ebtables的MAC SNAT / DNAT功能 . 我们没有其他理由在服务器上添加桥接接口,因为它们实际上并不通过多个接口桥接连接 .
我知道这是在服务器上添加桥接器的一个奇怪的原因,但我们在新项目中使用MAC SNAT / DNAT功能,而ebtables似乎是最安全,最快速和最简单的方式,因为我们已经非常熟悉iptables的 .
问题是,由于转换为br0接口,iptables PREROUTING转发到外部服务器不再有效 .
内部PREROUTING转发工作正常(例如:请求进入端口80,它转发到端口8080) .
OUTPUT链也可以工作(例如:我们可以通过本地目标IP:8080从盒子向外连接,OUTPUT链将它映射到不同服务器上的维护服务器IP,端口8080,并返回一个网页) .
但是,如果目标IP是外部的,那么进入框中的任何流量似乎都会在PREROUTING规则之后死亡 .
以下是我们的设置示例:
旧设置:
iptables -t nat -A PREROUTING -p tcp --dport 9080 -j DNAT --to-destination $MAINTIP:8080
iptables -a FORWARD --in-interface eth0 -j ACCEPT
iptables -t nat -A POSTROUTING --out-interface eth0 -j MASQUERADE
echo 1 > /proc/sys/net/ipv4/ip_forward
新设置:(尝试各种格式的旧设置......,尝试记录eth0和br0数据包)
iptables -t nat -A PREROUTING -p tcp --dport 9080 -j DNAT --to-destination $MAINTIP:8080
iptables -a FORWARD --in-interface br0 -j ACCEPT
iptables -t nat -A POSTROUTING --out-interface br0 -j MASQUERADE
echo 1 > /proc/sys/net/ipv4/ip_forward
在更改为br0之前,客户端请求将在端口9080处转到服务器A,然后将MASQUERADED转到另一台服务器$ MAINTIP .
如上所述,如果$ MAINTIP在同一台机器上,这可以正常工作,但如果它在另一台服务器上,则在新的br0设置下,数据包永远不会发送到$ MAINTIP .
我们希望数据包与他们进入的MASQUERADED接口相同,就像我们切换到使用单NIC桥接器(br0 / bridge-utils)之前一样 .
我尝试在iptables的所有阶段添加日志记录 . 出于某种原因,iptables TRACE目标在此设置上不起作用,因此我无法获得TRACE日志,但数据包显示在PREROUTING表中,但在此之后似乎默默地丢弃 .
我已经阅读了这篇优秀的文档,并对iptables和ebtables之间的流程有了更好的理解:http://ebtables.sourceforge.net/br_fw_ia/br_fw_ia.html
根据我的理解,似乎网桥没有将数据包转发到它们进入的相同接口,并且正在丢弃它们 . 如果我们添加了第二个接口,我想它会将它们转发到该接口(桥的另一端) - 这就是桥的工作方式;-)
是否有可能按照我们想要的方式完成这项工作,并将这些数据包通过他们所使用的相同界面进行PREROUTE / FORWARD,就像我们以前一样?
我希望有一些ebtables规则可以与iptables PREROUTING / FORWARD / POSTROUTING规则一起使用,使iptables转发按照通常的方式工作,并将路由数据包发送出br0(eth0)而不是丢弃它们 .
欢迎评论,火焰,任何和所有建议!
最好的问候,尼尔
2 回答
我猜你做到了,但是为了确定,你是否将eth0添加到了桥上?
虽然,我不确定问题是什么,但在调试bridge / ebtables / iptables问题时,我会提供一些可能有助于您或其他人的调试技巧:
确保"/proc/sys/net/bridge/bridge-nf-call-iptables"已启用(1)
这会导致桥接流量通过netfilter iptables代码 .
请注意,这可能会影响性能 .
通过ebtabels / iptables规则检查数据包拦截,
使用命令:
这可能有助于您了解流量是否匹配和截获 .
检查conntrack表中是否显示IP NAT流量:
要么
检查桥的MAC学习
在eth0和br0上使用tcpdump来检查两者是否按预期看到的数据包
使用-e选项也可以查看MAC地址 .
对于调试,尝试将网桥接口置于混杂模式,也许网桥接收具有不同MAC地址的数据包(在混杂模式下它也将接受不同的MAC)
也许将桥接前向延迟设置为0
并禁用stp(生成树协议)
你的路由表是什么样的?
尝试使用"dev br0"添加特定或默认路由规则
我希望它有点帮助......
祝好运
只有1.5岁,但可以用于以后的查找 . 刚才查看你的链接,它特别指出,如果MAC位于网桥的同一侧(而不是另一个端口或网桥本身(请参见链路中的图2.b),则brouting将忽略该数据包 .
除此之外,我只是引用此链接:http://wiki.squid-cache.org/ConfigExamples/Intercept/LinuxBridge
“... ebtables DROP vs iptables DROP
在大多数情况下用于过滤网络流量的iptables中,DROP目标意味着“数据包消失” .
在ebtables中,“-j redirect --redirect-target DROP”意味着“数据包从桥接器进入内核的上层,例如路由\转发”(< - 相关位!)
由于ebtables在连接的链路层工作以拦截连接,我们必须将流量“重定向”到iptables将能够拦截\ tproxy的级别 .
其中有你的答案(当然,为未来的访客增加了赌注,除非你还在,p)