Cen*_*oob 5 networking linux centos routing iptables
最初发布在 Unix 和 Linux 上,但没有人能够回答它,所以我将问题迁移到这里:
我的问题是关于 CentOS 5 上基于源的策略路由,带有 2 个 WAN 和一个带有负载平衡的 LAN (NAT) 端口,但在开始描述问题之前,首先要进行一些评论......
我知道这个话题在堆栈交换中被多次带到这里,似乎前 5 个答案是(从最多到最少排序):
大多数情况下,其中一些答案是正确的,但对我来说,解决方案 1 和 2 没有锻炼(我至少不会放弃第 2 点,因为我的设置可能存在一些问题),第 3 点基本上是隔离问题而不是解决它(也增加了路由表的复杂性)和解决方案 4 和 5 只是超出了范围,因为我没有资源购买专用硬件,也不能将服务器脱机,因为它正在生产中,所以总结更换具有“更好”功能的 CentOS 服务器不在讨论之列。
好的,现在回到问题中,让我们首先描述当前的设置......
接口:
eth1: IP: 10.0.0.1, GW: 10.0.0.1, NM: 255.255.255.0 (LAN)
eth0: IP: 10.0.1.1, GW: 10.0.1.254, NM: 255.255.255.0 (ISP1 - ADSL Router)
eth2: IP: 10.0.2.1, GW: 10.0.2.254, NM: 255.255.255.0 (ISP2 - ADSL Router)
Run Code Online (Sandbox Code Playgroud)
/etc/sysctl.conf:
# Controls IP packet forwarding
net.ipv4.ip_forward = 1
# Controls source route verification
net.ipv4.conf.default.rp_filter = 0
# Do not accept source routing
net.ipv4.conf.default.accept_source_route = 0
# Controls the use of TCP syncookies
net.ipv4.tcp_syncookies = 1
# Ignoring broadcasts request
net.ipv4.icmp_echo_ignore_broadcasts = 1
net.ipv4.icmp_ignore_bogus_error_messages = 1
Run Code Online (Sandbox Code Playgroud)
/etc/iproute2/rt_tables:
#
# reserved values
#
255 local
254 main
253 default
0 unspec
#
# local
#
#1 inr.ruhep
2 ISP1
3 ISP2
Run Code Online (Sandbox Code Playgroud)
/etc/sysconfig/network-scripts/route-eth0:
10.0.1.0/24 dev eth0 src 10.0.1.1 table ISP1
default via 10.0.1.254 dev eth0 table ISP1
Run Code Online (Sandbox Code Playgroud)
/etc/sysconfig/network-scripts/route-eth2:
10.0.2.0/24 dev eth2 src 10.0.2.1 table ISP2
default via 10.0.2.254 dev eth2 table ISP2
Run Code Online (Sandbox Code Playgroud)
/etc/sysconfig/network-scripts/rule-eth0:
fwmark 2 table ISP1
from 10.0.1.1 table ISP1
Run Code Online (Sandbox Code Playgroud)
/etc/sysconfig/network-scripts/rule-eth2:
fwmark 3 table ISP2
from 10.0.2.1 table ISP2
Run Code Online (Sandbox Code Playgroud)
/etc/sysconfig/iptables:
*filter
:INPUT DROP [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
# Basic Rules
-A INPUT -i lo -j ACCEPT
-A INPUT -i eth0 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A INPUT -i eth2 -m state --state RELATED,ESTABLISHED -j ACCEPT
# SSH
-A INPUT -i eth0 -m tcp -p tcp --dport 22 -j ACCEPT
-A INPUT -i eth2 -m tcp -p tcp --dport 22 -j ACCEPT
# OpenVPN
-A INPUT -i eth0 -m udp -p udp --dport 1194 -j ACCEPT
-A INPUT -i eth2 -m udp -p udp --dport 1194 -j ACCEPT
# Allow everything from LAN
-A INPUT -i eth1 -j ACCEPT
# Allow everything from the VPN
-A INPUT -i tun0 -j ACCEPT
# Default Drop on everything else
-A INPUT -j DROP
# Allow forwarding from LAN and VPN
-A FORWARD -i eth1 -j ACCEPT
-A FORWARD -i tun0 -j ACCEPT
# Allow all outbound traffic
-A OUTPUT -o lo -j ACCEPT
-A OUTPUT -o eth1 -j ACCEPT
COMMIT
*nat
:PREROUTING ACCEPT [0:0]
:POSTROUTING ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
# DNAT to Developer Box (SSH Server)
-A PREROUTING -i eth0 -p tcp -m tcp --dport 2222 -j DNAT --to-destination 10.0.0.200:2222
-A PREROUTING -i eth2 -p tcp -m tcp --dport 2222 -j DNAT --to-destination 10.0.0.200:2222
# SNAT
-A POSTROUTING -o eth0 -j SNAT --to-source 10.0.1.1
-A POSTROUTING -o eth2 -j SNAT --to-source 10.0.2.1
COMMIT
*mangle
:PREROUTING ACCEPT [0:0]
:INPUT ACCEPT [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
:POSTROUTING ACCEPT [0:0]
# Mark Based Routing? (based on NerdBoys site)
-A PREROUTING -j CONNMARK --restore-mark
-A PREROUTING --match mark --mark 2 -j ACCEPT
-A PREROUTING -i eth0 -j MARK --set-mark 2
-A PREROUTING --match mark --mark 3 -j ACCEPT
-A PREROUTING -i eth2 -j MARK --set-mark 3
-A PREROUTING -j CONNMARK --save-mark
COMMIT
Run Code Online (Sandbox Code Playgroud)
使用 gwping bash 脚本可以实现负载平衡,该脚本基本上监视 2 个广域网(eth0 和 eth2)并像这样在服务器中设置默认路由和权重(在负载均衡或 2 个广域网启动并运行时):
ip route replace default scope global nexthop via 10.0.1.1 dev eth0 weight 1 nexthop via 10.0.2.1 dev eth1 weight 1
Run Code Online (Sandbox Code Playgroud)
我遇到的问题是,即使使用这种设置,很多人似乎都同意是正确的设置,但从外部(特别是 ssh 开发人员框和 OpenVPN 框)访问网络内部服务时仍然存在问题,即使数据包正在被“标记”并相应地路由来自开发框的答案总是走错路。我不知道我是否在 mangle 或 nat 区域中遗漏了某些东西,或者我是否完全误解了基于源的路由,无论如何,如果有人知道如何相应地使这项工作正常进行,我们将不胜感激。
我的这个设置的来源是:
lartc.org/lartc.html#LARTC.RPDB.MULTIPLE-LINKS
fatalsite.net/?p=90
nerdboys.com/2006/05/05/conning-the-mark-multiwan-connections-using-iptables-mark-connmark-and-iproute2/
policyrouting.org/PolicyRoutingBook/ONLINE/CH08.web.html
unix.stackexchange.com/questions/58635/iptables-set-mark-route-diferent-ports-through-different-interfaces
unix.stackexchange.com/questions/22770/two-interfaces-two-addresses-two-gateways
bulma.net/body.phtml?nIdNoticia=2145
Run Code Online (Sandbox Code Playgroud)
最亲切的问候
PS1:我发现一个网站说路由表中的标记应该与iptables标记不同+1(kim.attr.ee/2010/08/source-based-policy-routing-on-centos.html)这是真的?或者这个网站超级不正确。
经过更多的研究和调试,我发现一个网站说我忘记在路由后表中添加 SNAT 部分,所以我将此规则添加到 iptables 配置中:
-A POSTROUTING --match mark --mark 2 -j SNAT --to-source 10.0.1.1
-A POSTROUTING --match mark --mark 3 -j SNAT --to-source 10.0.2.1
Run Code Online (Sandbox Code Playgroud)
但是我仍然无法从网络外部连接到devbox。从好的方面来说, a iptables -t nat -nvL POSTROUTING提示了基于 connmark 的策略路由的工作原理,因此它可能与 ISP1 和 ISP2 路由器边缘有关:
Chain POSTROUTING (policy ACCEPT 520 packets, 56738 bytes)
pkts bytes target prot opt in out source destination
0 0 SNAT all -- * * 0.0.0.0/0 0.0.0.0/0 MARK match 0x2 to:10.0.1.1
6 312 SNAT all -- * * 0.0.0.0/0 0.0.0.0/0 MARK match 0x3 to:10.0.2.1
903 70490 SNAT all -- * eth0 0.0.0.0/0 0.0.0.0/0 to:10.0.1.1
931 78070 SNAT all -- * eth2 0.0.0.0/0 0.0.0.0/0 to:10.0.2.1
Run Code Online (Sandbox Code Playgroud)
我还从我的设置中添加了更多信息,请有人给我一个救命稻草,因为我开始没有想法了...>.<
ip路由显示:
10.8.0.2 dev tun0 proto kernel scope link src 10.8.0.1
10.0.2.0/24 dev eth2 proto kernel scope link src 10.0.2.1
10.0.0.0/24 dev eth1 proto kernel scope link src 10.0.0.1
10.8.0.0/24 via 10.8.0.2 dev tun0
10.0.1.0/24 dev eth0 proto kernel scope link src 10.0.1.1
169.254.0.0/16 dev eth2 scope link
default
nexthop via 10.0.1.254 dev eth0 weight 1
nexthop via 10.0.2.254 dev eth2 weight 1
Run Code Online (Sandbox Code Playgroud)
ip规则显示:
0: from all lookup 255
1024: from all fwmark 0x2 lookup ISP1
1025: from all fwmark 0x3 lookup ISP2
2024: from 10.0.1.1 lookup ISP1
2025: from 10.0.2.1 lookup ISP2
32766: from all lookup main
32767: from all lookup default
Run Code Online (Sandbox Code Playgroud)
新来源:
sarcasmasaservice.com/2013/04/linux-routing-capabilities-my-abuse-thereof/
Run Code Online (Sandbox Code Playgroud)
最亲切的问候
好...
经过数千小时的调试、尝试不同的设置和 72 小时的大量生产测试,我找到了正确的解决方案/设置,问题出在 iptables 规则(mangle 部分)中,数据包在进来时显然被标记为正确但是当他们出来时,没有任何用于 dnat 的数据包,无论如何,这是我解决问题的最终可行解决方案:
/etc/sysconfig/iptables:
*filter
:INPUT DROP [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
# Basic Rules
-A INPUT -i lo -j ACCEPT
-A INPUT -i eth0 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A INPUT -i eth2 -m state --state RELATED,ESTABLISHED -j ACCEPT
# SSH
-A INPUT -i eth0 -m tcp -p tcp --dport 22 -j ACCEPT
-A INPUT -i eth2 -m tcp -p tcp --dport 22 -j ACCEPT
# OpenVPN
-A INPUT -i eth0 -m udp -p udp --dport 1194 -j ACCEPT
-A INPUT -i eth2 -m udp -p udp --dport 1194 -j ACCEPT
# Allow everything from LAN
-A INPUT -i eth1 -j ACCEPT
# Allow everything from the VPN
-A INPUT -i tun0 -j ACCEPT
# Default Drop on everything else
-A INPUT -j DROP
# Allow forwarding from LAN and VPN
-A FORWARD -i eth1 -j ACCEPT
-A FORWARD -i tun0 -j ACCEPT
# Allow all outbound traffic
-A OUTPUT -o lo -j ACCEPT
-A OUTPUT -o eth1 -j ACCEPT
COMMIT
*nat
:PREROUTING ACCEPT [0:0]
:POSTROUTING ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
# DNAT to Developer Box (SSH Server)
-A PREROUTING -i eth0 -p tcp -m tcp --dport 2222 -j DNAT --to-destination 10.0.0.200:2222
-A PREROUTING -i eth2 -p tcp -m tcp --dport 2222 -j DNAT --to-destination 10.0.0.200:2222
# SNAT
-A POSTROUTING -o eth0 -j SNAT --to-source 10.0.1.1
-A POSTROUTING -o eth2 -j SNAT --to-source 10.0.2.1
COMMIT
*mangle
:PREROUTING ACCEPT [0:0]
:INPUT ACCEPT [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
:POSTROUTING ACCEPT [0:0]
# CONNMARK Source Based Routing
-A PREROUTING -i eth0 -m state --state NEW,RELATED,ESTABLISHED -d 10.0.1.1 -j CONNMARK --set-mark 0x2
-A PREROUTING -i eth2 -m state --state NEW,RELATED,ESTABLISHED -d 10.0.2.1 -j CONNMARK --set-mark 0x3
-A PREROUTING -i eth1 -m connmark --mark 0x2 -j CONNMARK --restore-mark
-A PREROUTING -i eth1 -m connmark --mark 0x3 -j CONNMARK --restore-mark
-A OUTPUT -m state --state ESTABLISHED,RELATED -j CONNMARK --restore-mark
COMMIT
Run Code Online (Sandbox Code Playgroud)
显然,加上之前所有与 iproute 和 gwping 相关的设置(用于链路负载平衡和故障转移),解决方案成为可能,这要归功于来源 [1] 和 [2],两者都将我指向了不同的部分(Luca Gibelli 用于解决方案的 PREROUTING 部分和 Karl Bowden 的 OUTPUT 部分),我也住在这里一些其他网站的更多资源,这些资源为我指明了正确的方向。希望这有助于将来的另一个系统管理员。
最亲切的问候
资料来源:
[1]www.nervous.it/2010/09/dnat-and-ip-source-routing-woes/
[2]blog.khax.net/2009/12/01/multi-gateway-balancing-with-iptables/
[3]home.regit.org/netfilter-en/links-load-balancing/
[4]mailman.ds9a.nl/pipermail/lartc/2006q2/018964.html
[5]web.archive.org/web/20120320115329/http://versa.net.au/index.php?option=com_content&task=view&id=21&Itemid=34
Run Code Online (Sandbox Code Playgroud)
2013 年 10 月 10 日更新
OpenVPN 需要一个额外的配置指令来处理多 wan 设置(如前一个),因此只需在 server.conf 中添加 multihome 选项(OpenVPN >= 2.1,对于较低版本,只需将本地指令更改为仅侦听特定的 ip),你很高兴。
归档时间: |
|
查看次数: |
23067 次 |
最近记录: |