Take Linux Routing to the Next Level with iproute2
If you're an oldtyme network admin clinging possessively to your old Linux routing utilities in the net-tools package — ifconfig, route, arp, netstat, nameif, and so forth — it is perfectly OK if you continue to do so. They get the job done. However, they have some limitations that may matter to you.
With net-tools all packets are treated the same, and all routing is based only on the destination. This is OK if all you need are the simplest static routes. But if you want to be able to configure more complex scenarios simply and efficiently, or set up tunnels easily, or set different priorities depending on the type of data, or assign multiple IPs to an interface without using aliasing, you want iproute2.
Today we'll look at kernel requirements and useful iproute2 querying and status commands. Next week we'll configure both static and dynamic routes.
iproute2 is included in most distributions these days and replaces net-tools and any other motley old routing utilities you may have hanging around. The ip command does just about everything you need, so you don't need to collect and learn a lot of different utilities. The old gang in the net-tools package have been officially deprecated for quite a few years, but you know how these things hang on. You may also install iproute2 from sources or packages — both Debian and Red Hat packages are named iproute, not iproute2.
iproute2 On A Workstation
To use iproute2 on a non-router host — for example, for using the querying and interface-configuring commands on a workstation — requires only iproute2; you don't need to mess with kernel options. Use the ip command to see your interface status:
$ ip address show
1: lo: <LOOPBACK,UP> mtu 16436 qdisc noqueue
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
2: eth0: <BROADCAST,MULTICAST,UP> mtu 1500 qdisc pfifo_fast qlen 100
link/ether 00:03:6d:00:83:cf brd ff:ff:ff:ff:ff:ff
inet 192.168.1.5/24 brd 192.168.1.5 scope global eth0
As you can see, ip uses CIDR notation instead of moldy old dotted quads. This is what the output from an IPCop router/firewall looks like:
2: eth0: <BROADCAST,MULTICAST,UP> mtu 1500 qdisc pfifo_fast qlen 1000
link/ether 00:60:97:99:3f:21 brd ff:ff:ff:ff:ff:ff
inet 192.168.1.1/24 brd 192.168.1.255 scope global eth0
3: eth1: <BROADCAST,NOTRAILERS,UP> mtu 1500 qdisc pfifo_fast qlen 1000
link/ether 00:50:ba:54:91:6d brd ff:ff:ff:ff:ff:ff
inet 184.108.40.206/24 brd 220.127.116.11 scope global eth1
(If you're wondering what "qdisc pfifo_fast qlen" mean, see Chapter 9 of the Linux Advanced Routing & Traffic Control HOWTO.) You can see that eth0 is the "inward" facing NIC, because it has a non-routable private IP and broadcast address. eth1 is the "outward" facing NIC with a public routable IP.
Adding And Removing IPs
ip will assign new addresses directly to a NIC, rather than aliasing the way ifconfig does. This means that instead of treating each aliased address as a separate interface, the kernel sees it as a single interface. So it uses less memory, less table space, and less CPU time, which all add up in a hurry on large-scale systems. Adding a new address is easy:
# ip address add dev eth0 192.168.1.8
As is removing one:
# ip address delete dev eth0 192.168.1.8
Display Routing Tables
You can view your existing routing table:
$ ip route show
192.168.1.0/24 dev eth0 proto kernel scope link src 192.168.1.5
default via 192.168.1.1 dev eth0
"proto kernel" means the routing protocol is in the Linux kernel. If there are routes from a different router like Zebra it would mark the routes added by Zebra with "proto zebra." "scope link" tells us this is a unicast or broadcast route. Other values are "scope host" for local, and "scope global" marks gatewayed unicast routes. "default via 192.168.1.1 dev eth0" tells us the default route and the device it is attached to.
You can add some options to prune the output from complex routing tables. For example, you can find all the Zebra-added routes:
$ ip route show proto zebra
Or see what a particular interface is doing:
$ ip route show dev eth1
You can find out which route and IP are used to reach a particular IP, whicn is handy for troubleshooting:
$ ip route get 18.104.22.168
22.214.171.124 via 192.168.1.1 dev eth0 src 192.168.1.5
cache mtu 1500 advmss 1460 hoplimit 64
Display ARP Table
$ ip neigh show
192.168.1.1 dev eth0 lladdr 00:60:97:99:3f:21 nud reachable
192.168.1.10 dev eth0 lladdr 00:0a:e4:40:8b:fd nud stale
"nud" means "Neighbour Unreachability Detection." The first line of output tells you the IP, interface, and hardware (MAC) address, and that the host is up and reachable. On the second line "nud stale" means the host has not been contacted recently and the entry is ready to time out. Typically an entry in the cache has a lifetime of about 15 minutes. To refresh the ARP table entry simply ping the host.
Building A Router
To do actual routing requires that certain features are enabled in the kernel. All you need for basic routing is
This sample from /boot/config-2.6.8 file shows a complete routing feature set enabled. This shows every routing-related option available:
# Networking options
# CONFIG_IP_PNP is not set
# CONFIG_ARPD is not set
IP_PNP is for diskless terminals, and ARPD is obsolete and should not be used.
See how easy iproute2 is? You don't need to spend gobs of money on some expensive commercial thingy. Come back next week to learn how to build both static and dynamic routes.
- the Linux Advanced Routing & Traffic
- See man (8) ip for complete ip command options and definitions of terms shown in
the command outputs
- RFC 1123 - Requirements for Internet Hosts
- RFC 1812 - Requirements for IP Version 4 Routers
Spoonful Of CIDR Helps the Routing Tables Go Down
- IPCalc, for calculating IP