Iptables

Add the following content to a startup script, for example in /etc/rc.local:

IPTABLES=/sbin/iptables
EXTIF="eth0"
INTIF="eth1"

sysctl -w net.ipv4.conf.${EXTIF}.arp_ignore=1
sysctl -w net.ipv4.conf.${INTIF}.forwarding=1
sysctl -w net.ipv4.conf.${EXTIF}.forwarding=1

$IPTABLES -P INPUT ACCEPT
$IPTABLES -F INPUT
$IPTABLES -P OUTPUT ACCEPT
$IPTABLES -F OUTPUT
$IPTABLES -P FORWARD DROP
$IPTABLES -F FORWARD
$IPTABLES -t nat -F

$IPTABLES -A FORWARD -i $EXTIF -o $INTIF -m state --state ESTABLISHED,RELATED \
   -j ACCEPT
$IPTABLES -A FORWARD -i $INTIF -o $EXTIF -j ACCEPT
$IPTABLES -A FORWARD -j LOG
$IPTABLES -t nat -A POSTROUTING -o $EXTIF -j MASQUERADE

$IPTABLES -t nat -A PREROUTING -p tcp --dport 53 -i $INTIF \
   -j DNAT --to 10.0.2.3:53
$IPTABLES -t nat -A PREROUTING -p udp --dport 53 -i $INTIF \
   -j DNAT --to 10.0.2.3:53

 

This assumes the following:

  • eth0 is the network interface to the outside world (WAN) and eth1 is the network interface conntected to the internal network. This interface (eth1) should have a fixed IP address.
  • all existing iptables rules are to be deleted
  • outgoing traffic is always accepted, but incoming traffic is only accepted for already established or related connections (that were made from the inside)
  • the sender's IP address of outgoing traffic is replaced by the IP address of the router. The router takes care to deliver incoming traffic of established or related connections to the correct device / computer. This allows you to use arbitrary IP addresses on the internal network, because they are not seen, nor known, on the outside world. They only see the router's IP address. For internal networks it is best practice to use IP address ranges specifically created for use on private networks, like 10.x.y.z, 172.16.y.z or 192.168.y.z. Because the IP addresses on the internal network are not known on the outside world, you cannot reach computers on the internal network from the outside, unless you use port forwarding.
  • DNS queries from the inside are forwarded to the real DNS server. This way, you can configure computers on your internal network to use the router as the DNS server. Replacesysctl -w net.ipv4.conf.eth1.forwarding=1 10.0.2.3 by your real DNS server's IP address.

 

port forwarding

In order to forward incoming connections on port 1234 to the SSH port (22) of an internal machine with IP address 192.168.1.12, use:

$IPTABLES -t nat -A PREROUTING -i $EXTIF -p tcp --dport 1234 -j DNAT \
   --to 192.168.1.12:22
$IPTABLES -A FORWARD -i $EXTIF -o $INTIF -p tcp --dport 22 -j ACCEPT

 

The source and destination ports may differ, so you can use a different port after the first --dport option, in order to forward port 1234 to port 22 on the internal machine. This is useful in cases where you need to access the same port on multiple machines on the internal network.