Mettere in sicurezza un Server utilizzando IPTABLES

closeQuesto articolo è stato pubblicato 5 anni 6 mesi 30 giorni giorni fa quindi alcuni contenuti o informazioni presenti in esso potrebbero non essere più validi. Questo sito non è responsabile per eventuali errori causati da questo problema.

Per chi come me, gestisce un proprio VPS o anche un Server Dedicato Linux utilizzato come Webserver, anche se con un firewall fisico davanti (e poichè nessun server esposto su Internet è sicuro al 100%) è pur sempre richiesta e necessaria un minimo di sicurezza aggiuntiva.

Per questo motivo vi riporto di seguito un metodo per installare uno script “minimalista” interattivo, che utilizza iptables come firewall su Linux e permette di utilizzare:

  • Accesso SSH
  • DNS Server
  • NTP
  • FTP Server (Porte per modalità “Passive” da 30000 a 50000)
  • HTTP/HTTPS Webserver
  • Mailserver POP3/IMAP4/SMTP

avere protezione contro i SYN Flood e bloccare tutto ciò che non ci è necessario.

Ovviamente lo script può essere adattato secondo le nostre esigenze, aggiungendo o rimuovendo le porte non utilizzate dai servizi attivi sulla nostra installazione Linux.

L’installazione, è funzionante su sistemi RedHat, CentOS e derivate viene utilizzato il comando chkconfig.

Il corrispondente di chkconfig su Debian, Ubuntu e derivate è update-rc.d, per quest’ultimo comando potete dare un occhio a questo articolo.

Con pochi semplici passi possiamo effettuare l’installazione sia per RedHat, CentOS e derivate che per Debian, Ubuntu e derivate, ovviamente dove non indicato il Sistema Operativo, sono le parti comuni ad entrambi i sistemi.

ATTENZIONE: Tutti i comandi devono essere eseguiti da utente root, oppure, nei sistemi dove è permesso (Es: Ubuntu, Raspbian…), anteponendo “sudo” davanti al comando da eseguire.

– Effettuiamo il passaggio a utente “root”

sudo su -

– Arrestiamo il servizio IPTABLES

/etc/init.d/iptables stop

– Disabilitiamo il servizio IPTABLES

  • Per RedHat, CentOS e derivate
chkconfig iptables off
  • Per Debian, Ubuntu e derivate
update-rc.d iptables remove

– Copiamo il seguente codice su /etc/init.d/firewall (Es. vi /etc/init.d/firewall)
(Promemoria: Disabilitiamo l’opzione “a capo automatico” sul nostro editor di testo preferito.)

  • Per RedHat, CentOS e derivate
#!/bin/sh
# firewall
# chkconfig: 3 21 91
# descrizione: Avvia, arresta e riavvia firewall via iptables

case "$1" in
start)

# Cancellazione regole
iptables -t filter -F
iptables -t filter -X
echo - Cancellazione regole : [OK]

# SSH In
iptables -t filter -A INPUT -p tcp --dport 22 -j ACCEPT
echo - SSH : [OK]

# Non interrompere le established connections
iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
iptables -A OUTPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
echo - established connections : [OK]

# Blocca tutte le connessioni come predefinito
iptables -t filter -P INPUT DROP
iptables -t filter -P FORWARD DROP
iptables -t filter -P OUTPUT DROP
echo - Blocco tutte le connessioni : [OK]

# Protezione SYN-Flood
iptables -N syn-flood
iptables -A syn-flood -m limit --limit 10/second --limit-burst 50 -j RETURN
iptables -A syn-flood -j LOG --log-prefix "SYN FLOOD: "
iptables -A syn-flood -j DROP
echo - Protezione SYN-Flood : [OK]

# Interfaccia Loopback
iptables -t filter -A INPUT -i lo -j ACCEPT
iptables -t filter -A OUTPUT -o lo -j ACCEPT
echo - Loopback : [OK]

# ICMP (Ping)
iptables -t filter -A INPUT -p icmp -j ACCEPT
iptables -t filter -A OUTPUT -p icmp -j ACCEPT
echo - PING : [OK]

# DNS In/Out
iptables -t filter -A OUTPUT -p tcp --dport 53 -j ACCEPT
iptables -t filter -A OUTPUT -p udp --dport 53 -j ACCEPT
iptables -t filter -A INPUT -p tcp --dport 53 -j ACCEPT
iptables -t filter -A INPUT -p udp --dport 53 -j ACCEPT
echo - DNS : [OK]

# NTP Out
iptables -t filter -A OUTPUT -p udp --dport 123 -j ACCEPT
echo - NTP : [OK]

# FTP Out
iptables -t filter -A OUTPUT -p tcp --dport 20:21 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 30000:50000 -j ACCEPT
# FTP In
iptables -t filter -A INPUT -p tcp --dport 20:21 -j ACCEPT
iptables -t filter -A INPUT -p tcp --dport 30000:50000 -j ACCEPT
iptables -t filter -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
echo - FTP : [OK]

# HTTP + HTTPS Out
iptables -t filter -A OUTPUT -p tcp --dport 80 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 443 -j ACCEPT
# HTTP + HTTPS In
iptables -t filter -A INPUT -p tcp --dport 80 -j ACCEPT
iptables -t filter -A INPUT -p tcp --dport 443 -j ACCEPT
echo - HTTP/HTTPS : [OK]

# Mail SMTP:25
iptables -t filter -A INPUT -p tcp --dport 25 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 25 -j ACCEPT
echo - SMTP : [OK]

# Mail POP3:110
iptables -t filter -A INPUT -p tcp --dport 110 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 110 -j ACCEPT
echo - POP : [OK]

# Mail IMAP:143
iptables -t filter -A INPUT -p tcp --dport 143 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 143 -j ACCEPT
echo - IMAP : [OK]

echo - Firewall [OK]
exit 0
;;

stop)
echo "Arresto Firewall... "
iptables -P INPUT ACCEPT
iptables -P OUTPUT ACCEPT
iptables -t filter -F
echo "Firewall Arrestato!"
exit 0
;;

restart)
/etc/init.d/firewall stop
/etc/init.d/firewall start
;;

*)
echo "Utilizzo: /etc/init.d/firewall {start|stop|restart}"
exit 1
;;
esac
  • Per Debian, Ubuntu e derivate (grazie al commento di Andrea con l’integrazione)
#!/bin/sh
### BEGIN INIT INFO
# Provides: firewall
# Required-Start: $remote_fs $syslog
# Required-Stop: $remote_fs $syslog
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
# Short-Description: firewall via iptables
# Description: Avvia, arresta e riavvia firewall via iptables
### END INIT INFO

case "$1" in
start)

# Cancellazione regole
iptables -t filter -F
iptables -t filter -X
echo - Cancellazione regole : [OK]

# SSH In
iptables -t filter -A INPUT -p tcp --dport 22 -j ACCEPT
echo - SSH : [OK]

# Non interrompere le established connections
iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
iptables -A OUTPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
echo - established connections : [OK]

# Blocca tutte le connessioni come predefinito
iptables -t filter -P INPUT DROP
iptables -t filter -P FORWARD DROP
iptables -t filter -P OUTPUT DROP
echo - Blocco tutte le connessioni : [OK]

# Protezione SYN-Flood
iptables -N syn-flood
iptables -A syn-flood -m limit --limit 10/second --limit-burst 50 -j RETURN
iptables -A syn-flood -j LOG --log-prefix "SYN FLOOD: "
iptables -A syn-flood -j DROP
echo - Protezione SYN-Flood : [OK]

# Interfaccia Loopback
iptables -t filter -A INPUT -i lo -j ACCEPT
iptables -t filter -A OUTPUT -o lo -j ACCEPT
echo - Loopback : [OK]

# ICMP (Ping)
iptables -t filter -A INPUT -p icmp -j ACCEPT
iptables -t filter -A OUTPUT -p icmp -j ACCEPT
echo - PING : [OK]

# DNS In/Out
iptables -t filter -A OUTPUT -p tcp --dport 53 -j ACCEPT
iptables -t filter -A OUTPUT -p udp --dport 53 -j ACCEPT
iptables -t filter -A INPUT -p tcp --dport 53 -j ACCEPT
iptables -t filter -A INPUT -p udp --dport 53 -j ACCEPT
echo - DNS : [OK]

# NTP Out
iptables -t filter -A OUTPUT -p udp --dport 123 -j ACCEPT
echo - NTP : [OK]

# FTP Out
iptables -t filter -A OUTPUT -p tcp --dport 20:21 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 30000:50000 -j ACCEPT
# FTP In
iptables -t filter -A INPUT -p tcp --dport 20:21 -j ACCEPT
iptables -t filter -A INPUT -p tcp --dport 30000:50000 -j ACCEPT
iptables -t filter -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
echo - FTP : [OK]

# HTTP + HTTPS Out
iptables -t filter -A OUTPUT -p tcp --dport 80 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 443 -j ACCEPT
# HTTP + HTTPS In
iptables -t filter -A INPUT -p tcp --dport 80 -j ACCEPT
iptables -t filter -A INPUT -p tcp --dport 443 -j ACCEPT
echo - HTTP/HTTPS : [OK]

# Mail SMTP:25
iptables -t filter -A INPUT -p tcp --dport 25 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 25 -j ACCEPT
echo - SMTP : [OK]

# Mail POP3:110
iptables -t filter -A INPUT -p tcp --dport 110 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 110 -j ACCEPT
echo - POP : [OK]

# Mail IMAP:143
iptables -t filter -A INPUT -p tcp --dport 143 -j ACCEPT
iptables -t filter -A OUTPUT -p tcp --dport 143 -j ACCEPT
echo - IMAP : [OK]

echo - Firewall [OK]
exit 0
;;

stop)
echo "Arresto Firewall... "
iptables -P INPUT ACCEPT
iptables -P OUTPUT ACCEPT
iptables -t filter -F
echo "Firewall Arrestato!"
exit 0
;;

restart)
/etc/init.d/firewall stop
/etc/init.d/firewall start
;;

*)
echo "Utilizzo: /etc/init.d/firewall {start|stop|restart}"
exit 1
;;
esac

– Assegniamo permessi di esecuzione al nuovo servizio firewall

chmod 700 /etc/init.d/firewall

SOLO per RedHat, CentOS e derivate, aggiungiamo il servizio firewall tramite il comando “chkconfig”

chkconfig --add firewall

– Avvio automatico firewall al boot del sistema

  • Per RedHat, CentOS e derivate
chkconfig --level 2345 firewall on
  • Per Debian, Ubuntu e derivate
update-rc.d firewall defaults

– Avvio del firewall

/etc/init.d/firewall start

Oltre all’avvio automatico al boot, lo script può anche essere eseguito manualmente in qualsiasi momento con i seguenti comandi

– Per arrestare il firewall

/etc/init.d/firewall stop

– Per avviare il firewall

/etc/init.d/firewall start

– Per riavviare il firewall

/etc/init.d/firewall restart

Come abbiamo visto, in pochi semplici passi abbiamo reso sicuro il nostro sistema, permettendo l’accesso solo alle porte/servizi necessari e negando l’accesso a tutto ciò che non è attivo sul nostro sistema.

iptables firewall linux

5 Risposte

  1. filippo ha detto:

    qualche problema…
    # /etc/init.d/firewall start
    /etc/init.d/firewall: line 109: restart}.: command not found
    stop: missing job name
    Try `stop –help’ for more information.

    grazie.
    ciao

    • Morgan ha detto:

      Ciao Filippo e grazie per il commento.
      Lo script è per RedHat, CentOS e derivate, tu su che S.O. lo stai utilizzando?
      Sicuro di aver copiato lo script correttamente ed aver dato i diritti di esecuzione?
      Tutte le operazioni vanno effettuate da utente root, oppure, se effettuato da utente diverso, anteponendo il comando “sudo” (Es. sudo /etc/init.d/firewall start).

      • filippo ha detto:

        ciao Morgan,
        grazie per la risposta, scusami se non ti ho riscritto subito ma poi ho risolto immediatamente, il copia e incolla mi aveva trasformato il — in . lo script funziona benissimo. grazie. ciao

  2. Andrea ha detto:

    Ciao Morgan,
    anche se hai già inserito un link aggiungo una nota per chi usa Debian (magari Raspbian su RaspberryPi).
    Utilizzando il comando

    update-rc.d firewall defaults

    per aggiungere lo script firewall tra i servizi, mi veniva restituito “insserv: warning: script ‘firewall’ missing LSB tags and overrides”.

    E’ bastato aggiungere all’interno dello script (subito dopo le prime 4 righe) :

    ### BEGIN INIT INFO
    # Provides: firewall
    # Required-Start: $remote_fs $syslog
    # Required-Stop: $remote_fs $syslog
    # Default-Start: 2 3 4 5
    # Default-Stop: 0 1 6
    # Short-Description: firewall via iptables
    # Description: Avvia, arresta e riavvia firewall via iptables
    ### END INIT INFO

    ed ora il servizio è stato correttamente aggiunto e parte al boot del sistema.

    ciao
    andrea

    • Morgan ha detto:

      Grazie Andrea, effettivamente mancava la parte per Debian e derivate, quindi come da tuo commento, ho aggiornato l’articolo aggiungendo quest’ultima.
      Ora dovrebbe andar bene per le distro piú “blasonate”.
      Nuovamente grazie 😉

Lascia un commento

Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *