VoIP and Hacking

Rilevamento delle scansioni con PortSentry

by admin on Dec.01, 2009, under Hacking, Linux, Sicurezza, Tools

Portsentry è un celebrato attack detection tool sviluppato originariamente da Psionic Technologies (poi assorbita da Cisco).
Anche se il progetto portsentry (http://sourceforge.net/projects/sentrytools/) non è più stato aggiornato dal 2003, ciò non significa che esso non sia tuttora valido, anzi, può succedere che risvegli un rinnovato interesse in un periodo come l’attuale, in cui i worms, che rappresentano l’agente infettivo di maggior peso, tipicamente eseguono scansioni automatiche a partire da hosts infetti alla ricerca di altre macchine vulnerabili, e possono rivelare così la propria presenza.

Il compito di PortSentry consiste nella rilevazione di scansioni e nella risposta a tali scansioni.
La scansione di una rete o di un sistema costituisce il prerequisito di un eventuale attacco e conseguente possibile intrusione. A meno che un attaccante conosca in anticipo quali porte siano aperte o disponibili su di un sistema, inizierà una scansione per determinare quali servizi l’host stia eseguendo. Qui è dove PortSentry entra in gioco, monitorando le porte TCP ed UDP del sistema e, a seconda di come sia configurato, rispondendo in modo appropriato ad una scansione identificata come tale.
PortSentry è in grado di rilevare anche scansioni di tipo stealth come quelle attuate da Nmap.

Portsentry può usare sei differenti modalità, impostabili a seconda di come il programma viene inizializzato .

- La prima modalità è “-tcp” che sarebbe anche la modalità di base. Con quest’opzione portsentry si impegnerà al controllo delle porte TCP presenti nel file di configurazione nella sezione “port configuration”. Potrà controllare fino a un massimo di 64 porte.

- La seconda è “-udp” e fa le stesse cose della precedente opzione, ma stavolta per quanto riguarda le porte UDP.

Quando PortSentry viene installato come pacchetto precompilato sotto Ubuntu, viene predisposto un init script (/etc/init.d/portsentry), che, leggendo le impostazioni presenti in /etc/default/portsentry:

#
TCP_MODE="tcp"
UDP_MODE="udp"
#

avvia per default il programma nella modalità di base, sia per TCP che per UDP:

# ps aux |grep portsentry |grep -v grep
root 3183 0.0 0.0 1692 488 ? Ss Nov30 0:00 /usr/sbin/portsentry -tcp
root 3187 0.0 0.0 1692 492 ? Ss Nov30 0:00 /usr/sbin/portsentry -udp

Effettuando una prima scansione di tipo TCP connect(), nel range delle porte di default, verso una macchina protetta da PortSentry, la scansione semplicemente tenterebbe di connettersi alle porte predefinite.
Se una connessione viene ultimata, la porta è in ascolto. Se la connessione non viene ultimata, la porta è chiusa.

Dando il comando:

# nmap -sT 172.16.0.1

otteniamo il seguente output:

Starting Nmap 5.00 ( http://nmap.org ) at 2009-11-29 17:22 CET
Interesting ports on localhost (172.16.0.1):
Not shown: 983 closed ports
PORT STATE SERVICE
1/tcp open tcpmux
79/tcp open finger
80/tcp open http
111/tcp open rpcbind
119/tcp open nntp
143/tcp open imap
1080/tcp open socks
1524/tcp open ingreslock
2000/tcp open callbook
3306/tcp open mysql
6667/tcp open irc
12345/tcp open netbus
31337/tcp open Elite
32771/tcp open sometimes-rpc5
32772/tcp open sometimes-rpc7
32773/tcp open sometimes-rpc9
32774/tcp open sometimes-rpc11

Nmap done: 1 IP address (1 host up) scanned in 0.41 seconds

Risultano molte più porte in stato open ora che PortSentry è in esecuzione. Ciò avviene perché portsentry (così avviato) effettua un bind verso ogni porta che monitorizza, non facendo uso di sockets raw, che non necessitano il bind a una specifica porta. Quando PortSentry viene avviato, informa lo stack TCP/IP dell’ host che desidera porsi in ascolto sulla lista di porte che gli sono state assegnate. Da questo momento quando una richiesta di connessione arriva su quella porta, lo stack completera la richiesta e inoltrerà i dati per PortSentry. Tale metodo, al contrario di quando si utilizzano raw sockets, ha alcuni evidenti svantaggi:
PortSentry offre la visione ad un attaccante che vi sia una moltitudine di open ports disponibili ad un exploit sulla macchina vittima. Anche se ciò non è vero, certamente attira comunque interesse e rende perciò la macchina sempre più un possibile target. L’ attaccante può anche realizzare che la macchina è sorvegliata da PortSentry osservando quali porte risultano aperte. Usando tecniche di scansione più avanzate sarebbe in grado di evaderlo, potendo determinare esattamente quali porte evitare di scansionare con tecniche più rumorose, e scegliendo invece di sondare porte che sa non essere guardate da PortSentry.

Portsentry identifica puntualmente il verificarsi di una scansione di tipo Connect, come è verificabile dall’osservazione del file /var/log/syslog:

[...]
portsentry[19331]: attackalert: Connect from host: 172.16.0.2/172.16.0.2 to TCP port: 635
portsentry[19331]: attackalert: Host: 172.16.0.2 is already blocked. Ignoring
portsentry[19331]: attackalert: Connect from host: 172.16.0.2/172.16.0.2 to TCP port: 1524
portsentry[19331]: attackalert: Host: 172.16.0.2 is already blocked. Ignoring
[...]

Proviamo ora ad effettuare un tentativo di scansione SYN stealth verso il computer vittima.

# nmap -sS 172.16.0.1

Una scansione SYN stealth invia un iniziale SYN packet alla macchina vittima, ma non risponde al pacchetto SYN,ACK , ed invia invece un pacchetto REST, con ciò terminando immediatamente il tentativo di connessione.

Dal punto di vista dell’attaccante il risultato della scansione è di fatto analogo al precedente, dato che vengono rilevate le stesse porte di prima in stato open.
Portsentry invece non rileva la scansione, e semplicemente ignora tali tentativi, dal momento che nessuna connessione viene di fatto ultimata.

L’ attaccante, comunque, riceve un packet SYN,ACK , che gli indica che vi è un servizio in attesa su tale porta. Se la presenza di PortSentry, come precedentemente determinato, darà l’impressione di servizi che non esistono, PortSentry non rileverà tali scansioni. In base al prevedibile set di risposte ricevute, corrispondente ad una installazione di default di PortSentry, l’ attaccante verrà allertato sulla presenza del nostro IDS, senza far rilevare la propria presenza. Il comando nmap -sS 172.16.0.1, dato sulla macchina attaccante, genererà lo stesso risultato di nmap -sT 171.16.0.1, ma non venendo rilevato.

Un attaccante potrebbe anche scegliere di utilizzare scansioni UDP contro una macchina vittima, dato che molti servizi vulnerabili operano su UDP.
Dato che la comunicazione UDP è connectionless, nessuna risposta può venire sollecitata da parte della vittima. Deve perciò venire utilizzata una altra tecnica. Pacchetti UDP di tipo Null (pacchetti di 0 byte) vengono inviati alla macchina vittima. Un host che riceva un pacchetto UDP destinato ad una porta closed dovrebbe emettere un messaggio ICMP port unreachable.
Se nessuna risposta viene ricevuta, si assume che la porta sia open. Sfortunatamente, se lo stealth mode non è attivato, PortSentry effettua il bind alle porte che sta monitorando ed esse appaiono quindi open se scansionate. Vantaggi e svantaggi relativamente a scansioni UDP contro hosts protetti da PortSentry sono fondamentalmente simili, perciò, a quelli delle scansioni TCP di tipo connect().
Le scansioni UDP possono anche risultare esasperatamente lente, in base ad un suggerimento presente in RFC 1812 (4.3.2.8) che limità la generazione dei messaggi di errore ICMP, meccanismo alla base di questo tipo di scansione. Per tale motivo le scansioni UDP possono risultare lente ed inaccurate, e non vengono generalmente usate da attaccanti che non siano interessati a qualche servizio UDP in maniera più mirata. Tuttavia, una volta che un host sia stato compromesso, esso può venire usato per lanciare insidiose scansioni UDP all’interno della rete locale. La capacità di PortSentry di rilevare scansioni di tipo UDP qui risulta importante se viene usata allo scopo di scoprire hosts compromessi o attacchi interni. A livello perimetrale, although PortSentry does a fine job of detecting UDP scans (when told to with the command portsentry -udp), implement a firewall rule preventing ICMP port unreachable messages from leaving, thereby rendering external UDP scans useless.

- La terza modalità con cui si può avviare portsentry è “-stcp”, dove la “s” significa stealth. Questa opzione e la successiva sono disponibili solo per Linux. Con l’opzione “-stcp” , portsentry usa una socket per monitorare i pacchetti in arrivo, in questo modo, cioè, la porta non effettua alcun binding.
- La quarta è “-sudp” e fa le stesse cose della precedente opzione ma relativamente alle porte UDP.
Tramite le modalità appena menzionate siamo ora in grado di avviare PortSentry in stealth mode. In tale modalità, PortSentry opera utilizzando raw sockets. Ciò non richiede il binding da parte di PortSentry a singole porte per osservare il traffico destinato ad esse. Poterlo fare richiede i privilegi di root, poiché si sta ora operando a livello di kernel, esaminando i pacchetti prima che lo faccia il TCP.

Proviamo ora ad avviare una scansione nmap di tipo connect (-sT) contro una macchina protetta da PortSentry operante in stealth mode:
Per inciso la porta 22 è chiusa ma non coperta da portsentry, la porta 1 invece lo è, mentre sulla porta 80 è realmente in ascolto un server Apache.

# nmap -n -sT --reason -p 1,22,80 172.16.0.1

Starting Nmap 5.00 ( http://nmap.org ) at 2009-11-29 23:01 CET
Interesting ports on 172.16.0.1:
PORT STATE SERVICE REASON
1/tcp closed tcpmux conn-refused
22/tcp closed ssh conn-refused
80/tcp open http syn-ack
[...]

Poiché questa volta PortSentry non completa la connessione in presenza di una richiesta, solo le porte con reali servizi in esecuzione dietro ad esse vengono identificate come open (essendolo realmente).
Ora che PortSentry opera in stealth mode è altrettanto capace tuttavia di rilevare scansioni del tipo SYN stealth, ad esempio:

# nmap -n -sS --reason 172.16.0.1

Starting Nmap 5.00 ( http://nmap.org ) at 2009-11-30 11:37 CET
Interesting ports on 172.16.0.1:
Not shown: 998 closed ports
Reason: 998 resets
PORT STATE SERVICE REASON
80/tcp open http syn-ack
111/tcp open rpcbind syn-ack
[...]

Una scansione SYN rivelerà le stesse information della precedente scansione connect(), e sebbene risulti normalmente più difficile da individuare, PortSentry in questo caso svolge egregiamente il proprio compito, come testimoniato dal seguente estratto di /var/log/syslog:

[...]
… portsentry[2081]: attackalert: TCP SYN/Normal scan from host: 172.16.0.2/172.16.0.2 to TCP port: 32774
… portsentry[2081]: attackalert: Ignoring TCP response per configuration file setting.
… portsentry[2081]: attackalert: TCP SYN/Normal scan from host: 172.16.0.2/172.16.0.2 to TCP port: 6667
… portsentry[2081]: attackalert: Host: 172.16.0.2/172.16.0.2 is already blocked Ignoring
[...]

A questo punto possiamo anche toglierci la curiosità di verificare il comportamento di PortSentry in presenza degli altri tipi di scansione stealth che fanno parte dell’arsenale di nmap:

FIN scans - Tali scansioni utilizzano pacchetti col flag TCP FIN settato. Tipicamente i pacchetti FIN sono presenti solo nell’ambito della sequenza di chiusura di una connessione. Pacchetti FIN inviati ad una porta TCP chiusa dovrebbero causare l’emissione di un pacchetto RST in risposta.

# nmap -n -sF --reason 172.16.0.1

Starting Nmap 5.00 ( http://nmap.org ) at 2009-11-30 12:16 CET
Interesting ports on 172.16.0.1:
Not shown: 998 closed ports
Reason: 998 resets
PORT STATE SERVICE REASON
80/tcp open|filtered http no-response
111/tcp open|filtered rpcbind no-response
[...]

La scansione ha risultato identico a quello che avrebbe avuto se la macchina target non fosse guardata da PortSentry, mentre viceversa quest’ultimo è in grado di rilevare esattamente l’esatto tipo di scansione subita, come osservabile in /var/log/syslog:

[...]
… portsentry[18613]: attackalert: TCP FIN scan from host: 172.16.0.2/172.16.0.2 to TCP port: 2000
… portsentry[18613]: attackalert: Ignoring TCP response per configuration file setting.
… portsentry[18613]: attackalert: TCP FIN scan from host: 172.16.0.2/172.16.0.2 to TCP port: 143
… portsentry[18613]: attackalert: Host: 172.16.0.2/172.16.0.2 is already blocked Ignoring
[...]

NULL scans - Le scansioni NULL usano pacchetti senza alcun flag TCP settato. Ancora una volta, in base alla RFC 793, ciò dovrebbe provocare l’invio di un pacchetto RST in risposta.

E’ esattamente quanto avviene lanciando una scansione come:

# nmap -n -sN --reason 172.16.0.1

che viene rilevata anch’essa con precisione da parte di PortSentry:

[...]
… portsentry[18613]: attackalert: TCP NULL scan from host: 172.16.0.2/172.16.0.2 to TCP port: 31337
[...]

XMAS scans - Le scansioni XMAS hanno i flags FIN, URG, e PUSH settati nel header TCP. Ancora una volta, essendo pacchetti tecnicamente “non normali” se presenti in internet (o anche in una LAN locale), dovrebbero provocare un pacchetto RST in presenza di una porta in stato closed.

E’ ancora quanto avviene con una scansione come

# nmap -n -sX --reason 172.16.0.1

rilevata ancora una volta con precisione da PortSentry:

[...]
… portsentry[18613]: attackalert: TCP XMAS scan from host: 172.16.0.2/172.16.0.2 to TCP port: 12345
… portsentry[18613]: attackalert: Host: 172.16.0.2/172.16.0.2 is already blocked Ignoring
[...]

FULL-XMAS scan - Tale tipo di scansione ha tutti i TCP flags settati (SYN,ACK,RST, FIN,URG,PSH). Un simile tipo di pacchetto non dovrebbe mai essere possibile in una LAN e tantomeno in Internet.
Si può attuare la scansione con:

# nmap -n --scanflags SYN,ACK,RST,FIN,URG,PSH --reason 172.16.0.1

Sebbene la scansione non venga stavolta rilevata da PortSentry, non porta nessun risultato utile a chi la effettua (nessuna risposta, e quindi qualsiasi porta considerata open|filtered

- La quinta e la sesta modalità di avvio per PortSentry sono “-atcp” e “-audp”. Queste sono le opzioni maggiormente efficaci (la “a” sta per advanced).
In presenza di queste opzioni portsentry legge il file di configurazione, e controlla gli scan dalla porta 1 fino al tetto indicato. Default = 1024.
Viene consigliato di non oltrepassare tale limite, benche’ sia possibile arrivare a 65535. In pratica tutte le porte disponibili.
Utilizzando le opzioni -atcp e -audp avremo anche la possibilita’ di inserire nel file /etc/portsentry/portsentry.conf una lista di porte che non saranno sorvegliate. Lo scopo di tale esclusione e’ inpedire dei falsi positivi relativamente a porte il cui utilizzo e’ comune.

Il più importante files di configurazione di PortSentry è /etc/portsentry/portsentry.conf. Qui è possibile indicare a PortSentry come reagire ad eventuali scansioni.
La prima sezione (Port Configurations) riguarda le porte controllate da portSentry in tcp mode o stealth tcp mode (TCP_PORTS), e in udp mode o stealth udp mode (UDP_PORTS).
La seconda sezione (Advanced Stealth Scan Detection Options) riguarda la modalità operativa quando PortSentry viene avviato coi parametri -atcp e -audp. In questo ambito ADVANCED_PORTS_TCP indica il limite numerico oltre il quale la corrispondente porta non viene controllata, mentre ADVANCED_EXCLUDE_TCP elenca i numeri di porta da escludere dal controllo, anche se compresi nel range definito in precedenza.
Analogo discorso vale per i corrispettivi parametri UDP (ADVANCED_PORTS_UDP e ADVANCED_EXCLUDE_UDP)
La successiva sezione (Configuration Files) riguarda i files usati da portsentry per scopi di history (HISTORY_FILE) o per definire gli hosts da ignorare (IGNORE_FILE) o raccogliere quelli da bloccare (BLOCKED_FILE).
La successiva sezione di configurazione (Misc. Configuration Options) permette di attivare o disattivare il DNS lookup.
Le successive sezioni consentono di stabilire in che modo portsentry reagirà nelle varie situazioni.
Innanzitutto ci sono le opzioni della sezione Ignore Options. Si puo scegliere di reagire alle scansioni (1), non reagire (0) o far partire un comando esterno (2). Le variabili di configurazione che controllano se PortSentry debba rispondere a una scansione oppure no, sono BLOCK_TCP e BLOCK_DUP.
Se si è scelto di reagire alle scansioni, nella sezione “dropping routes”, si potrà dire a portsentry dove indirizzare i pacchetti o quali regole di packet filtering utilizzare. Sono già presenti numerosi esempi per molte piattaforme.
PortSentry può inserire una route nella tabella di routing dell’host così che tutto il traffico proveniente dall’indirizzo IP che origina la scansione è inviato allo stesso “bit-bucket”. Utilizzare in tal modo la routing table dell’host per reindirizzare il traffico proveniente dall’host originante la scansione verso un indirizzo IP non esistente rende il sistema simile ad un buco nero … traffico vi entra, ma niente ne esce. Un problema inerente a questo metodo è che esso fa aumentare di dimensioni la routing table di un host. Teoricamente un attaccante potrebbe forgiare l’indirizzo sorgente dei pacchetti usati nella scansione per fare in modo che PortSentry aggiunga indiscriminatamente nuove voci alla routing table. Ciò potrebbe esaurire la memoria del sistema ospite e generare problemi di performance.
Per utilizzare una soluzione di questo tipo, nella sezione Dropping Routes occorre impostare una variabile KILL_ROUTE simile alla seguente:

KILL_ROUTE="/sbin/route add -host $TARGET$ gw 333.444.555.666"

Tipicamente il route gateway dovrebbe corrispondere ad un IP inattivo o “dead host”.
PortSentry può anche contare su vari software packages di firewalling (dalla versione 2.0 i firewalls supportati da PortSentry sono ipfw, ipfilter, ipfwadm, ipchains, ed iptables) in modo tale che una regola di firewalling possa venire usata per bloccare il traffico a partire dall’indirizzo IP all’origine della scansione. In tal modo PortSentry rileverebbe una scansione e quindi aggiungerebbe una appropriata regola alla configurazione del firewall . Questo implica il blocco sull’ IP dell’host originale. Ancora una volta, come avviene usando la tabella di routing per bloccare le scansioni, anche questo meccanismo può venire abusato. Un attaccante dotato di un certo skill, facendo uso di pacchetti forgiati può fare in modo che PortSentry escluda degli hosts legittimi indiscriminatamente (L’esperienza indica comunque questa possibilità come molto remota).
Se qualcosa del genere ha un a qualche possibilità di avvenire è più probabile che avvenga a carico di UDP. Gli hosts che eseguono PortSentry dovrebbero essere strettamente monitorati (Psionic Technologies raccommenda l’utilizzo del loro prodotto LogSentry al fine di monitorare i logfiles di PortSentry) per assicurare che l’ host non sta bloccando traffico legittimo.

Una soluzione di tale tipo la si attiva comunque impostando la variabile KILL_ROUTE come in:

KILL_ROUTE="/sbin/iptables -I INPUT -s $TARGET$ -j DROP"

Infine, e la cosa viene fatta nella sezione TCP Wrappers, una regola per TCP wrapper relativa all’indirizzo IP attaccante può venire aggiunta al file /etc/hosts.deny. Utilizzando il metodo dei TCP wrappers, PortSentry aggiunge semplicemente l’host all’origine della scansione al file /etc/hosts.deny. Ciò non blocca una scansione, ma previene l’attaccante dal connettersi da quell’indirizzo a servizi protetti da TCP wrappers sull’ host target. Questa non è una protezione così forte come quella derivante dall’ uso di voci della routing table o del firewall; tuttavia, offre il vantaggio di non generare facilmente un denial of service di sè stessi.
Il formato della relativa variabile KILL_HOSTS_DENY può essere del tipo:

KILL_HOSTS_DENY="ALL: $TARGET$ : DENY"

e dare quindi origine ad un file /etc/hosts.deny con un contenuto simile:

[...]
ALL: 207.189.253.70 : DENY
ALL: 82.255.250.84 : DENY
ALL: 95.25.156.158 : DENY
[...]

La successiva sezione External Command permette di definire un comando da eseguire quando un host tenta la connessione.
Questa opzione indica la capacità da parte di PortSentry di mandare in esecuzione un comando esterno prima o dopo che l’host all’irigine della scansione sia bloccato. Ciò viene impostato dalla opzione KILL_RUN_CMD. Tale comand può consistere in qualsiasi cosa, da un reverse finger ad una completa controscansione verso l’host attaccante. Se tale comando debba essere eseguito prima o dopo che PortSentry abbia reagito bloccando (tipicamente) il traffico da quel sorgente viene determinato con la opzione KILL_RUN_CMD_FIRST. Impostandola a ‘1′ fa in modo che PortSentry esegua il comando esterno prima che PortSentry avvii la reazione di risposta alla scansione. Un valore pari a ‘0′ viceversa dopo. Estrema cura deve essere impiegata quando si configura tale opzione.
Una variabile importante da configurare nel file portsentry.conf è il valore di SCAN_TRIGGER. Quest’ultimo controlla il numero di connessioni ad una porta controllata che PortSentry permette prima di considerare una risposta. Per default è impostato a ‘0′, il che fa in modo che PortSentry reagisca immediatamente ad una scansione. Tale variabile può venire impostata a un valore positivo qualsiasi, ma gli autori del programma sconsigliano valori più grandi di 2.
L’ultima sezione (Port Banner Section), riguarda la visualizzazione di un banner in caso di tentativo di intrusione. Non è possibile attivare questa possibilità, definita tramite la variabile PORT_BANNER, se si è in stealth mode.

Send post as PDF to PDF | PDF Creator | PDF Converter
:, , , , , ,

Comments are closed.

Cerchi qualcosa in particolare?

Usa il form qui sotto per cercare nel sito:

Blogroll!

Alcuni links...

Archives

Tutte le entries, in ordine cronologio...