IPTables for CentOS
Whenever you get a new RedHat or CentOS instance you want to secure it by setting up firewall rules using the builtin in iptables . If you spinoff an Amazon EC2 instance then you’d be doing the equivalent using Security Groups, which are a slightly higher level concept but essentially performs the same function. If running a VPS on barebones CentOS, iptables is the easiest option.
Word of Caution: Its easy to lock yourself out of the system if you make a mistake when configuring iptables. I prefer writing all the rules in a script file, double checking the commands to make sure I’m not closing SSH on port 22. Also, its a good idea to remain logged in the current SSH shell after executing iptables rules and then attempt to login in a new SSH shell to ensure you still have access to the server.
Here’s the outline of what we’ll do:
- create file iptables_setup.sh
- execute file iptables_setup.sh
- setup rsyslog using iptables.conf
- setup log rotation for iptables.log
Here’s the iptables_setup.sh file that you can create in your home directory and execute once to setup iptables and save these rules so that system reloads these rules on server reboot.
#!/bin/bash
# File: /home/my-user/iptables_setup.sh
# Flush all current nat rules
iptables -t nat -F
# Flush all current rules from iptables
iptables -F
# Set access for localhost
iptables -A INPUT -i lo -j ACCEPT
iptables -A INPUT -s 127.0.0.1 -d 127.0.0.1 -j ACCEPT
iptables -A INPUT -s 127.0.0.1 -d 127.0.0.1 -j ACCEPT
# Accept packets belonging to established and related connections
iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
# Secure SSH on port 22 and prevent repeated login attempts. If someone tries to connect
# 4 or more times on port 22 within 300secs, drop all packets from that host. As soon as
# 300secs have elapsed between connection attempts, iptables will forget the host and it
# will be allowed to try and connect again.
# 1. Remote host addr of all connects on port 22 is logged to temporary list
# 2. Create a new chain LOGDROP
# 3. If host addr exists in temporary list, has 4 or more hits within 300secs jump to LOGDROP
# 4. All remaining connects can proceed and accept SSH connection
# 5. For LOGDROP chain pass packets to logging facility, prefix "iptables deny: " to msg
# 6. For LOGDROP chain drop the packets
iptables -A INPUT -p tcp -m tcp --dport 22 -m state --state NEW -m recent --set --name DEFAULT --rsource
iptables -N LOGDROP
iptables -A INPUT -p tcp -m tcp --dport 22 -m state --state NEW -m recent --update --seconds 300 --hitcount 4 --name DEFAULT --rsource -j LOGDROP
iptables -A INPUT -p tcp -m tcp --dport 22 -j ACCEPT
iptables -A LOGDROP -j LOG --log-prefix "iptables deny: " --log-level 4
iptables -A LOGDROP -j DROP
# Lock down the system
iptables -P INPUT DROP
iptables -P FORWARD DROP
iptables -P OUTPUT ACCEPT
# Open DNS and HTTP ports
iptables -A INPUT -p tcp -m tcp --dport 53 -j ACCEPT
iptables -A INPUT -p udp -m udp --dport 53 -j ACCEPT
iptables -A INPUT -p tcp -m tcp --dport 80 -j ACCEPT
iptables -A INPUT -p tcp -m tcp --dport 443 -j ACCEPT
# Save settings
service iptables save
# List rules
iptables -L -v
The following iptables.conf file defines the message format and content for iptables.log
# File: /etc/rsyslog.d/iptables.conf
:msg,contains,"iptables deny:" /var/log/iptables.log
& ~
The following file defines the log rotation policy and frequency for iptables.log
# File: /etc/logrotate.d/iptables
/var/log/iptables.log {
daily
missingok
notifempty
rotate 7
size 25M
delaycompress
dateext
maxage 30
postrotate
invoke-rc.d rsyslog reload > /dev/null
endscript
}