Friday, April 8, 2011

Load balance 2 WAN links BASH script

BASH script to load balance 2 WAN links.

#!/bin/bash
#
# bal_local Load-balance internet connection over two local links
#
# Version: 1.0.0 - Fri, Sep 26, 2008
#
# Author: Niels Horn
#

# Set devices:
DEV1=${1-eth0} # default eth0
DEV2=${2-ppp0} # default ppp0

# Get IP addresses of our devices:
ip1=`ifconfig $DEV1 | grep inet | awk '{ print $2 }' | awk -F: '{ print $2 }'`
ip2=`ifconfig $DEV2 | grep inet | awk '{ print $2 }' | awk -F: '{ print $2 }'`

# Get default gateway for our devices:
gw1=`route -n | grep $DEV1 | grep '^0.0.0.0' | awk '{ print $2 }'`
gw2=`route -n | grep $DEV2 | grep '^0.0.0.0' | awk '{ print $2 }'`

echo "$DEV1: IP=$ip1 GW=$gw1"
echo "$DEV2: IP=$ip2 GW=$gw2"

### Definition of routes ###

# Check if tables exists, if not -> create them:
if [ -z "`cat /etc/iproute2/rt_tables | grep '^251'`" ] ; then
echo "251 rt_dev1" >> /etc/iproute2/rt_tables
fi
if [ -z "`cat /etc/iproute2/rt_tables | grep '^252'`" ] ; then
echo "252 rt_dev2" >> /etc/iproute2/rt_tables
fi

# Define routing tables:
ip route add default via $gw1 table rt_dev1
ip route add default via $gw2 table rt_dev2

# Create rules:
ip rule add from $ip1 table rt_dev1
ip rule add from $ip2 table rt_dev2

# If we already have a 'nexthop' route, delete it:
if [ ! -z "`ip route show table main | grep 'nexthop'`" ] ; then
ip route del default scope global
fi

# Balance links based on routes:
ip route add default scope global nexthop via $gw1 dev $DEV1 weight 1 nexthop via $gw2 dev $DEV2 weight 1

# Flush cache table:
ip route flush cache

# All done...

To use the script, copy it to /usr/local/bin, make it executable with 'chmod +x' and call it with:
bal_local

10 comments:

Shafiq Mustapa said...

bro, kau dah test tak script ni? aku test kat ubuntu ada error

Error: an inet address is expected rather than "table".
Error: an IP address is expected rather than "dev"

aku pun tak berapa paham sebab tak pernah main ip route apetah lagi iptables. agak2 ape maksud error tu?

thanks

zamri said...

Sorry lambat reply. Pastikan ko check dulu variable $gw1 dan $gw2 ada nilai yg dia dapat dari baris gw1=`route -n | grep $DEV1 | grep '^0.0.0.0' | awk '{ print $2 }'`

Shafiq Mustapa said...

thanks for reply.

ip semua dah kasi dan dah dapat. ada error dekat line 38/39 dan 43/44. yang pelik bila aku copy/paste run kat terminal takde error, tapi run dalam script ada error.

http://pastebin.com/y9eXc0zN

thanks.

zamri said...

Ini shell script. Mmg utk run dalam terminal. Kalau nak run selain dari terminal, maybe perlukan sedikit modification. Kalau run dalam terminal, adakah loadbalance berlaku?

Shafiq Mustapa said...

run dalam terminal ./loadbal.sh . bila run, error diatas yang keluar. cuma apabila part error dilarikan asing as single command, no error detected.

zamri said...

adakah ko run sbg root?

Shafiq Mustapa said...

run as root pun sama error run as user.

zamri said...

hmmm.. maybe ada error di mana2.

Ni hasil aku run dlm laptop aku utk baris dapatkan IP tu:


[root@asus ~]# IP1=`ifconfig wlan0 | grep "inet addr" | awk '{ print $2 }' | awk -F: '{ print $2}'`
[root@asus ~]# echo $IP1
192.168.1.12

Aku modified sikit utk ambil hanya IPv4. Cuba manually satu2 line utk cari punca error.

Vidyadhar Hullur said...

while running this script am getting error like :
RTNETLINK answers : file exists

zamri said...

That error can be ignored.