Translation(s): English
WARNING: nftables is the default firewall framework since Debian 10 Buster. This page is outdated.
Contents
Introduction
A network firewall is a set of rules to allow or deny passage of network traffic, through one or more network devices. A network firewall may also perform more complex tasks, such as network address translation, bandwidth adjustment, provide encrypted tunnels and much more related to network traffic.
Prior to version 5 (Lenny), a default Debian installation, did not have a default firewall enabled. But provides the needed tools to configure it manually.
Basic firewall software
Network traffic has different components, layers and protocols. For more references, check out the links section.
The most known type of firewall, and the most initially implemented, are sets of rules based on netfilter software, based on a set of kernel modules and some user space tools.
Basic software for network traffic manipulation
The default Debian installation comes with the program iptables(8), configured to allow all traffic. This section briefly explains the different programs to handle network traffic manually, as well as two sample scripts.
You need to be root, or use sudo, to launch these programs.
You may find the iptables-persistent package useful.
Using iptables for IPv4 traffic
This is not an iptables manual, only a short introduction about the use of the program. For more extended explanations, see iptables(8)
Basic invocation to define rules is:
% iptables [-t table] -[AD] chain rule-specification [options]
Tables and chains
All rules, are stored on different tables.
The default table is filter, which maintain the INPUT, OUTPUT and FORWARD chains, used for incoming, outgoing and redirected traffic respectively.
Other present tables are mangle, nat and raw. You can also create and delete custom tables.
Rules and program invocation may refer to a specific table using the -t table_name switch (or --table table_name).
If no table is specified, the default table is used (the filter table).
To list the ruleset of any table, the -L switch is used. For example:
% iptables -L Chain INPUT (policy ACCEPT) target prot opt source destination Chain FORWARD (policy ACCEPT) target prot opt source destination Chain OUTPUT (policy ACCEPT) target prot opt source destination
As you can see, the default policy in a default installation is to ACCEPT all traffic. There are no rules on any chain.
Each of the default tables, contain different chains, to store rules for different points, in the kernel networking subsystem.
You can list other tables using -t, for example, to see the nat (Network Address Translation) table:
% iptables -L -t nat Chain PREROUTING (policy ACCEPT) target prot opt source destination Chain POSTROUTING (policy ACCEPT) target prot opt source destination Chain OUTPUT (policy ACCEPT) target prot opt source destination
Matching and order
When a packet is inspected through the rulesets, matches are searched from top to bottom of tables and chains.
Into the rules, matches are searched from left to right, of the rule syntax used.
When a packet does not match a rule, the search jumps to the next rule. If no rules matches, then the default policy is applied to the packet.
If the packet matches any rule definition, then the target defined on the rule is applied (ACCEPT, REJECT, DROP, LOG, etc), and the following rules of the same chain are skipped.
It is very important to keep this in mind when designing a ruleset, to reach the desired functionality and because of its impact on performance, in large rulesets.
Policies and Targets
Default policy is to ACCEPT all traffic, but the most common practice, is to change policies to DROP all traffic but the allowed.
You have to be careful and sure that your rules are right, before put a policy to DROP, or you will lose connectivity.
See the troubleshooting section for tips about this issue.
Program switches
Most commonly used switches are:
-A Add this rule at the end of the defined chain.
-D Delete this rule definition from the ruleset.
-I Insert this rule at the beginning of the defined chain.
-P Change the default policy of a chain.
There are other switches, to handle chains, tables, clear rules, counters and other elements. See iptables(8) man page.
Modules
The iptables program has an extensive collection of modules, to use different criteria to evaluate packets.
There are modules for protocols, logging, states of the conection, etc. All compiled-in modules, are neatly explained in the man page.
Modules may have parameters (-m module_name --parameter_name parameter_arguments).
An example rule, using the state module, to drop incoming traffic with INVALID state (a parameter of the state module), defined in the headers of the packet, would be:
% iptables -I INPUT -m state --state INVALID -j DROP
Example scripts
Installation
You can put this scripts at any place that run at boot time or network initialization.
Common places are:
/etc/rc.local
Before the exit 0. Will be launched at boot time.
#!/bin/sh # # rc.local # # This script is executed at the end of each multiuser runlevel. # Make sure that the script will "exit 0" on success or any other # value on error. # # In order to enable or disable this script just change the execution # bits. # # By default this script does nothing. set -e # Launch my netfilter rules if [ -e '/etc/firewall_example.sh' ] then /bin/sh '/etc/firewall_example.sh' fi exit 0
/etc/network/interfaces
This is a more reasonable and standard place for networking related stuff.
For example, if eth0 is your main or uniq interface, using DHCP:
# This file describes the network interfaces available on your system # and how to activate them. For more information, see interfaces(5). # The loopback network interface auto lo iface lo inet loopback # WAN cablemodem allow-hotplug eth0 iface eth0 inet dhcp pre-up /bin/sh /etc/firewall/enable.sh post-down /bin/sh /etc/firewall/disable.sh
SystemD | firewall.service
Most Debian distributions now include systemd. In order to bring up the iptable rules using systemd at start:
Create a new file using any reasonable file text editor(I called mine firewall.service)
# vim.tiny /etc/systemd/system/firewall.service
Then add the following:
[Unit] Description=Add Firewall Rules to iptables [Service] Type=oneshot ExecStart=/etc/firewall/enable.sh #ExecStart=/etc/firewall/enable6.sh #For IPV6 [Install] WantedBy=multi-user.target
Then enable the service:
# systemctl enable firewall.service
Example: Basic standalone machine firewall
You can use this script in any stand-alone machine (for example a personal desktop) that does not need ports open to any place. Or see the final commented line, to open specific ports.
A simple script like the one below, will provide your host with a reasonable amount of security. Be aware that the following script drops all packets which do not match an allow rule, so normal network error messages will not be seen. All allow rules have been commented out to protect the uninitiated.
#!/bin/sh # A very basic IPtables / Netfilter script /etc/firewall/enable.sh PATH='/sbin' # Flush the tables to apply changes iptables -F # Default policy to drop 'everything' but our output to internet iptables -P FORWARD DROP iptables -P INPUT DROP iptables -P OUTPUT ACCEPT # Allow established connections (the responses to our outgoing traffic) iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT # Allow local programs that use loopback (Unix sockets) iptables -A INPUT -s 127.0.0.0/8 -d 127.0.0.0/8 -i lo -j ACCEPT # Uncomment this line to allow incoming SSH/SCP conections to this machine, # for traffic from 10.20.0.2 (you can use also use a network definition as # source like 10.20.0.0/22). # iptables -A INPUT -s 10.20.0.2 -p tcp --dport 22 -m state --state NEW -j ACCEPT
Example: Basic gateway machine firewall
#!/bin/sh # This is a more complex setup, for a home firewall: # * One interface plug to the ISP conection (eth0). Using DHCP. # * One interface plug to the local LAN switch (eth1). Using 192.168.0.0/24. # * Traffic open from the LAN to the SSH in the firewall. # * Traffic open and translated, from the local LAN to internet. # * Traffic open from internet, to a local web server. # * Logging of dropped traffic, using a specific ''log level'' to configure a separate file in syslog/rsyslog. PATH='/sbin' ## INIT # Flush previous rules, delete chains and reset counters iptables -F iptables -X iptables -Z iptables -t nat -F # Default policies iptables -P INPUT DROP iptables -P OUTPUT DROP iptables -P FORWARD DROP echo -n '1' > /proc/sys/net/ipv4/ip_forward echo -n '0' > /proc/sys/net/ipv4/conf/all/accept_source_route echo -n '0' > /proc/sys/net/ipv4/conf/all/accept_redirects echo -n '1' > /proc/sys/net/ipv4/icmp_echo_ignore_broadcasts echo -n '1' > /proc/sys/net/ipv4/icmp_ignore_bogus_error_responses # Enable loopback traffic iptables -A INPUT -i lo -j ACCEPT iptables -A OUTPUT -o lo -j ACCEPT # Enable statefull rules (after that, only need to allow NEW conections) iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT iptables -A OUTPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT iptables -A FORWARD -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT # Drop invalid state packets iptables -A INPUT -m conntrack --ctstate INVALID -j DROP iptables -A OUTPUT -m conntrack --ctstate INVALID -j DROP iptables -A FORWARD -m conntrack --ctstate INVALID -j DROP ## INPUT # Incoming ssh from the LAN iptables -A INPUT -i eth1 -s 192.168.0.0/24 \ -p tcp --dport 22 -m conntrack --ctstate NEW -j ACCEPT ## OUTPUT # Enable al outgoing traffic to internet iptables -A OUTPUT -o eth0 -d 0.0.0.0/0 -j ACCEPT # Enable access traffic, from the firewall to the LAN network iptables -A OUTPUT -o eth1 -d 192.168.0.0/24 -j ACCEPT ## FORWARD # We have dynamic IP (DHCP), so we've to masquerade iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE iptables -A FORWARD -o eth0 -i eth1 -s 192.168.0.0/24 \ -m conntrack --ctstate NEW -j ACCEPT # Redirect HTTP (tcp/80) to the web server (192.168.0.2) iptables -t nat -A PREROUTING -i eth0 -p tcp --dport 80 \ -j DNAT --to-destination 192.168.0.2:80 iptables -A FORWARD -i eth0 -p tcp --dport 80 \ -o eth1 -d 192.168.0.2 \ -m conntrack --ctstate NEW -j ACCEPT ## LOGGING iptables -A INPUT -j LOG --log-level DEBUG --log-prefix '[FW INPUT]: ' iptables -A OUTPUT -j LOG --log-level DEBUG --log-prefix '[FW OUTPUT]: ' iptables -A FORWARD -j LOG --log-level DEBUG --log-prefix '[FW FORWARD ]: '
Using ip6tables for IPv6 traffic
Because of growth, Internet is slowly switching to IPv6, that has a much larger address space than IPv4, and Debian is IPv6 capable.
If you have IPv6 addresses, networks and conections in your firewall, you've to be careful and configure your rulesets for each protocol.
To configure and manage IPv6 rulesets, you need to use ip6tables(8), which is provided by the default Debian install, in the package iptables.
The usage and functionality, is very similar to iptables, but oriented to IPv6 traffic.
For more references, see: ip6tables(8)
Example:
#!/bin/sh # A very basic IP6tables / Netfilter6 script PATH='/sbin' # Flush the tables to apply changes ip6tables -F #ACCEPT POLICY ip6tables -P INPUT DROP #If it doesn't match a rule Drop it ip6tables -P FORWARD DROP #NO ROUTING POLICY DROP ip6tables -P OUTPUT ACCEPT #If it doesn't match a rule ######## ip6tables -A INPUT -i lo -j ACCEPT ip6tables -m state --state ESTABLISHED,RELATED -A INPUT -j ACCEPT ip6tables -A INPUT -p icmpv6 -j ACCEPT
Using ebtables for ARP traffic
Ebtables (package ebtables) is used to set up, maintain, and inspect the tables of Ethernet frame rules in the Linux kernel. It is analogous to iptables, but operates at the MAC (ARP) layer, rather than the IP layer.
If you need to filter or translate ARP traffic (at link layer), your firewall has bridged interfaces (for example a transparent bridge between a OpenVPN tunneled VLAN and a local VLAN, or bridged interfaces for virtualization), ebtables(8) is your friend.
The design is very similar to netfilter's iptables.
It manages rulesets in tables with chains and targets, using user space tools, but this time it's not in the default Debian installation, and you need to add it:
% aptitude update % aptitude install ebtables
For a more detailed explanation of its usage, look at the inevitable man page, and visit the official website (see links section).
There are documents that explain howto integrate ebtables and iptables, using the iptables module physdev.
Application firewalls
To go more up, and manipulate the Layer 7 of the OSI model, and be able to define rules at application level, you need other tools.
For example... you open the port 80 to your users, but you don't want them to be able to download .exe files from internet. You need an application firewall or proxy.
The default kernel in Debian does not have layer 7 patches, but you can install user space proxys to manage this kind of filters.
There are options like squid, dans guardian, zorp, etc.
?Zorp is written in python and has been added to Debian with 5.0.
See also the links section for the l7-filter project.
Troubleshooting software and tips
Some helpful (and must-have) tools are:
ip(8): (package: iproute) to list interfaces, addresses, route tables, etc.
nc(1): (package: netcat) to test tcp and udp connections, open ports, etc.
ping(8): to test ICMP traffic (not tcp or udp).
tail(1): and other tools to monitor logs.
tcpdump(8): (package: tcpdump) to monitor "raw" packets, traffic, etc. using filters and regular expresions.
It's very easy to lose connectivity when initially configuring a firewall. And it's easier the more complex the firewall is.
A basic skill for troubleshoot a firewall problem, is to know the points where the traffic passes, is turned, routed, can be rejected, etc. And to know how to monitor that points, and what is happening.
The most effective is to analyze the traffic from end to end, from the initial request, the DNS, the interfaces by which must pass, the translations that have to do, the rejected traffic logs, the routing rules, etc.
A common hack when doing ruleset designing, is to put a cron task, that flush rules every few minutes, in case you will make a mistake (working in remote).
Graphic applications and frontends
There are some tools, to configure firewalls using frontends and helpers.
Some of them are:
Search firewall in packages.debian.org
There are also command line "high level" tools, to avoid the "low level" syntax, or to simplify certain tasks. Anyway, the real power is in the large number of modules and options for basic command line programs, that often is not covered by frontends.
Related articles
HowTo/shorewall - Configuring your firewall
HowTo/dnsmasq - Adding DHCP and DNS to your firewall
?HowTo/dansguardian - Adding web content filtering
?HowTo/openvpn - Adding a SSL VPN server (my prefered VPN solution)
HowTo/openswan - Adding a IPSEC VPN server
?HOWTO/DynamicBlockSSHddos - Simple script to do dynamic ssh ddos attack blocking
External Links
Networking information :
Ebtables :
Netfilter (iptables/ip6tables) :
Layer 7 :
Note
This page was completely changed by -- ?PoisonBit 2009-05-10 18:35:50. It has user oriented content. May be you want to improve it, and link from/to related pages. May be you want to create a developer oriented page about firewalls.
CategorySystemAdministration | CategorySystemSecurity | CategoryRedundant: merge with DebianFirewall