CentOS Routing with multiple ISPs

I searched everywhere for a simple solution to routing through two ISPs.  There are more complex examples that balance the routing using round robin or whatever, but I wanted a simple port based solution.  So, after spending literally hours reviewing other people’s stuff, which never actually worked, I finally figured it out.

1. Create a new file for when the interfaces come up.  The table “gaming” was named by me.  eth2 is my second interface, which I want my games to use.  Everything else using the internet goes out on eth1.

ip route flush table gaming
ip rule del fwmark 4 table gaming
ip route add table gaming default dev eth2
ip rule add fwmark 4 table gaming

2. Modify your iptables file to include a mangle section.  Essentially, we mark the packets for use by the ifup-local routing configuration, which looks at packets marked with a number 4.

:PREROUTING ACCEPT [31362:13297416]
:INPUT ACCEPT [2661:185691]
:FORWARD ACCEPT [28701:13111725]
:OUTPUT ACCEPT [1914:245407]
:POSTROUTING ACCEPT [30649:13358626]
# tda-desktop on gaming net
#-A PREROUTING -s -j MARK --set-xmark 0x4/0xffffffff
# nichole-pc-eth on gaming net
#-A PREROUTING -s -j MARK --set-xmark 0x4/0xffffffff
# see /sbin/ifup-local for routing based on this mark.
# CS:GO on the gaming ADSL
-A PREROUTING -p udp -m udp --dport 24015:24070 -j MARK --set-xmark 0x4/0xffffffff
-A PREROUTING -p udp -m udp --dport 25015:25070 -j MARK --set-xmark 0x4/0xffffffff
-A PREROUTING -p udp -m udp --dport 27015:27070 -j MARK --set-xmark 0x4/0xffffffff
# Planet Side 2 on the gaming ADSL
-A PREROUTING -p udp -m udp --dport 20040:20199 -j MARK --set-xmark 0x4/0xffffffff
-A PREROUTING -p udp -m udp --dport 5062 -j MARK --set-xmark 0x4/0xffffffff
# all of people's connections...
# tda-desktop
#-A PREROUTING --source -j MARK --set-xmark 0x4/0xffffffff


3. For machines that you want to be included in the dual routing, you need to masquerade them on both outgoing interfaces so that they can do normal traffic on eth1, and gaming on eth2.  So, in your “nat” section, add this, where is an IP allowed to do dual routing.  Remember though, any machine trying to use the ports defined earlier, will not get a connection unless you add both of these.  So, you’ll either need to include them here, or be more specific in the packet marking above (i.e. define them by IP and port, before marking)

-A POSTROUTING -o eth1 --source -j MASQUERADE
-A POSTROUTING -o eth2 --source -j MASQUERADE

4. And don’t forget to drop packets that weren’t established from inside.  In other words, we don’t want people faking that something was masqueraded…

-A INPUT -i eth2 -p tcp -m state --state NEW -m tcp -j DROP
-A INPUT -i eth2 -p udp -m state --state NEW -m udp -j DROP

If something is not working with this, please let me know.  I did this awhile back, and it’s possible I’ve forgotten a step, and I can take a look.

Some google search terms…

– linux iptables multiple interfaces

– linux iptables multiple connections