Evitar ataques DoS a apache con mod_evasive

El ataque DoS (Denegación de Servicio / Denial of Service) o DDoS (Distributed Denial of Service, denegación de servicio distribuida), es un ataque a un sistema de servidores o red que causa que un servicio o recurso sea inaccesible a usuarios legítimos. El flujo masivo de peticiones (a través del protocolo TCP/IP) al servidor y los ataques de fuerza bruta provocan el colapso de la red, o la saturación del servidor en cuestión.

En esta entrada vamos a tratar de paliar los ataques DoS centrados en el servicio Apache, que consiste básicamente en lanzar peticiones al servidor web de forma masiva hasta colapsar el mismo. Gracias al módulo de apache mod_evasive conseguiremos redirigir el tráfico de esta peticiones ilegítimas hacia un error 403 (prohibido).

La última versión estable de mod_evasive puede descargarse en este enlace.
Compilación:

cd /root/descargas
wget http://www.zdziarski.com/projects/mod_evasive/mod_evasive_1.10.1.tar.gz
tar -zxf mod_evasive_1.10.1.tar.gz
cd mod_evasive

Si usamos apache1, deberemos compilar su módulo correspondiente (adecuad la siguiente línea a vuestra ruta de apache):

/usr/local/apache/bin/apxs -cia mod_evasive.c

Si usamos apache2, deberemos compilar su módulo correspondiente:

/usr/local/apache/bin/apxs -cia mod_evasive20.c

Veremos que tras la compilación, automáticamente ya carga el módulo en nuestro httpd.conf:

LoadModule evasive_module libexec/mod_evasive.so

Configuración:

El fichero de configuración (muestro los valores por defecto) lo cargaremos en un fichero aparte y lo llamaremos desde el httpd.conf (podéis cargar las opciones directamente en el httpd.conf, yo lo pongo separado para una mejor estructuración) :

Include «/usr/local/apache/conf/mod_evasive.conf»

Y el fichero que incluye las configuraciones del módulo:

DOSHashTableSize 3097
DOSPageCount 2
DOSSiteCount 50
DOSPageInterval 1
DOSSiteInterval 1
DOSBlockingPeriod 10
DOSEmailNotify correo@dominio.com
DosWhitelist 98.54.48.14 # Ip ficticia

Vamos a explicar un poco lo que es cada opción:

Podemos ver lo que es cada cosa en:

DOSHashTableSize

Cuanto más grande sea el tamaño de la tabla de Hash, más memoria requerirá, pero el rastreo de Ips será más rápido. Es útil aumentar su tamaño si nuestro servidor recibe una gran cantidad de peticiones, pero así mismo la memoria del servidor deberá ser también mayor.

DOSPageCount

Número de peticiones a una misma página para que una IP sea añadida a la lista de bloqueo, dentro del intervalo de bloqueo en segundos especificado en el parámetro DOSPageInterval

DOSSiteCount

Igual que ‘DOSPageCount’, pero corresponde al número de peticiones al sitio en general, usa el intervalo de segundos especificado en ‘DOSSiteInterval’.

DOSPageInterval
Intervalo en segundos para el parámetro umbral de DOSPageCount.

DOSSiteInterval
Intervalo en segundos para el parámetro umbral DOSSiteCount.

DOSBlockingPeriod
Periodo de bloqueo para una IP si se supera alguno de los umbrales anteriores.El usuario recibirá un error403 (Forbidden) cuando sea bloqueado, si el atacante lo sigue intentando, este contador se reseteará automáticamente, haciendo que siga más tiempo bloqueada la IP.

DOSEmailNotify
Dirección de correo electrónico que recibirá información sobre los ataques.

DosWhitelist
Podemos especificar una IP o rango que será excluido del rastreo por mod_evasive.

Si alguna de estas opciones no os han quedado claras, indicadmelo y trataré de explicarlo de otra forma. Es fácil comprenderlo en inglés, pero su traducción se hace complicada.

Finalmente reiniciamos apache y ejecutamos el script en perl de testeo (test.pl) que viene incluido en el .tar.gz . Si todo ha ido bien, veremos que al cabo de unas cuantas peticiones, bloqueará el acceso al servicio web:

HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 200 OK
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden

HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden

Con esto ya tendríamos un protector de ataques DDoS a apache funcionando. No obstante, os puede ser de utilidad el siguiente comando, que nos indicará el nº de peticiones al puerto 80 por cada IP en el momento que lo ejecutemos:

netstat -plan|grep :80 | awk {‘print $5’}|cut -d: -f 1|sort|uniq -c|sort -n

Si solo queremos ver las establecidas:

netstat -plan|grep :80 | grep ESTABLISHED | awk {‘print $5’}|cut -d: -f 1|sort|uniq -c|sort -n

Esto es muy útil, pues a partir de dichos comandos, podemos averiguar rápidamente si una o varias IPs están haciendo un exceso de peticiones al servicio apache (fuerza bruta), y directamente filtrar la IP que queramos en nuestro firewall, por ejemplo en APF:

/usr/local/sbin/apf -d

De este modo, junto a la instalación de APF y BFD, nuestro servidor será menos vulnerable a ataques.

Como instalar y configurar BFD (Brute Force Detector)

BFD (Brute Force Detection), es un script en shell que parsea los logs de los diferentes servicios (ssh, ftp, apache, exim…) y chequea en busca de fallos repetitivos de autenticación, exceso de conexiones desde determinadas IPs, etc.

Combinado con APF (click aquí para acceder a una guía de instalación y configuración) forman un sistema de protección realmente bueno para nuestro sistema, ya que BFD le indicará a APF que IPs debe bloquear para que su acceso al servidor sea denegado (lo explicamos ahora):

Instalación de BFD:

La instalación es extremadamente sencilla:

cd /root/descargas
wget http://www.rfxnetworks.com/downloads/bfd-current.tar.gz
tar -xvzf bfd-current.tar.gz
cd bfd-0.7
./install.sh

Una vez hecho esto, nos indicará las rutas a ejecutables y ficheros de configuración:

.: BFD installed
Install path: /usr/local/bfd
Config path: /usr/local/bfd/conf.bfd
Executable path: /usr/local/sbin/bfd

Configuración de BFD:

Editamos el fichero de configuración con nuestro editor favorito:

vi /usr/local/bfd/conf.bfd

Activamos las alertas de ataque (cambiamos de 0 a 1), y configuramos que nos envíe un email por cada una:

ALERT_USR=»1″
EMAIL_USR=»tucuenta@tudominio.com»

Para evitar que el sitema bloquee nuestra IP local, la añadimos al fichero que guarda las IPs a ignorar en el rastreo, añadiremos p.ej. 192.168.1.1 en:

vi /usr/local/bfd/ignore.hosts

Ejecutamos el programa:

/usr/local/sbin/bfd -s

BFD chequeará los logs cada X tiempo, el que le indiquemos en su cron, por defecto cada 10 minutos:

[root@localhost ~]# cat /etc/cron.d/bfd
MAILTO=
SHELL=/bin/sh
#*/5 * * * * root /usr/local/sbin/bfd -q

Una vez comprendido esto, podéis personalizar las reglas que vienen por defecto para cada servicio, se encuentra en la siguiente ubicación:

/usr/local/bfd/rules

Con lo que más podéis jugar es con el valor “TRIG”, que indica el nº de conexiones o intentos permitidos para cada servicio, configuradlo en función de las necesidades de cada servicio:

TRIG=»45″

Con un poco más de paciencia, y estudiando cada regla puede personalizarse completamente, no obstante la seguridad de nuestro servidor, teniendo BFD + APF ha mejorado notablemente.

Fuente: rm-rf.es

Instalar APF (Advanced Policy Firewall) en sistema Unix

En esta entrada vamos a proteger nuestro sistema Unix con APF (Advanced Policy Firewall).

APF es un sistema de Firewall basado en IPtables, con la peculiaridad de que su manejo e instalación es extremadamente sencilla. Próximamente explicaremos también como instalar BFD, un detector de ataques de fuerza bruta, que unido a APF forman un excelente nivel de seguridad en el servidor, pues trabajan de forma conjunta.

Comenzamos con la instalación de APF:

cd /root/descargas (o la carpeta en la que guardes tus sources)
wget http://rfxnetworks.com/downloads/apf-current.tar.gz
tar -zxf apf-current.tar.gz
cd apf-0.*
./install.sh

Una vez instalado nos indicará las distintas rutas de ficheros de configuración y ejecutables:

Installation Details:
Install path: /etc/apf/
Config path: /etc/apf/conf.apf
Executable path: /usr/local/sbin/apf
AntiDos install path: /etc/apf/ad/
AntiDos config path: /etc/apf/ad/conf.antidos
DShield Client Parser: /etc/apf/extras/dshield/

Comenzamos a configurar APF, abirmos el fichero de configuración con nuestro editor favorito, estas son las opciones principales a configurar, recordad leer los comentarios en el fichero de configuración y en los README:

vi /etc/apf/conf.apf

Desactivamos/activamos el cron que desactiva el firewall cada 5 minutos, es útil activarlo mientras estemos de pruebas, pero aseguraos de dejarlo en 0 cuando el server entre en producción:

# Set firewall cronjob (devel mode)
# 1 = enabled / 0 = disabled
DEVEL_MODE=»1″

Interfaces de red que APF va a rastrear su tráfico, ponemos la interfaz que salga a Internet, en este caso es la eth1:

# Untrusted Network interface(s); all traffic on defined interface will be
# subject to all firewall rules. This should be your internet exposed
# interfaces. Only one interface is accepted for each value.
# NOTE: The interfacing structure is being worked towards support of MASQ/NAT
IFACE_IN=»eth1″
IFACE_OUT=»eth1″

Por otro lado, podemos configurar que ciertas interfaces no sean rastreadas por el firewall, pueden ser interfaces de tráfico local:

# Trusted Network interface(s); all traffic on defined interface(s) will by-pass
# ALL firewall rules, format is white space or comma seperated list.
IFACE_TRUSTED=»eth0″

Y para terminar la configuración básica, la parte más importante, la sección de puertos, configurable dependiendo de los puertos abiertos necesarios para cada servidor:

Puertos de entrada TCP permitidos:

# Common ingress (inbound) TCP ports
IG_TCP_CPORTS=»21,25,80,110,443,465″

Puertos de entrada UDP permitidos:

# Common ingress (inbound) UDP ports
IG_UDP_CPORTS=»»

Puertos de entrada ICMP permitidos:

# Common ICMP (inbound) types
# ‘internals/icmp.types’ for type definition; ‘all’ is wildcard for any
IG_ICMP_TYPES=»3,5,11″

Después están las mismas opciones, pero para salida, configurar según los requerimientos de cada uno. Y recordad revisar todas las demás opciones para sacar el mayor partido a este excelente firewall.

Otros dos ficheros importantes a tener en cuenta son :

/etc/apf/deny_host.rules
/etc/apf/allow_host.rules

En estos ficheros podemos incluir ips, rangos y reglas a las que denegar acceso (deny_host.rules) o permitir(allow_host.rules) al servidor. Finalmente arrancamos APF:

/usr/local/sbin/apf -s

Fuente: rm-rf.es

Como actualizar a WordPress 2.7

Ya está aquí la nueva versión 2.7 de WordPress, viene con bastantes cambios de apariencia y funcionalidad a nivel de dashboard, os dejo un vídeo en el que se pueden observar todas estas novedades. La actualización es tán sencilla como las anteriores, puedes descargarlo y encontrar la guía de actualización/instalación en este enlace.

Expresiones Regulares – Las Bases

Expresiones Regulares – Las Bases

Introducción

Todos los programadores de perl han usado las expresiones regulares en algun momento, ya sea para verificar si alguna variable tiene un valor deseado, o para sustituir una palabra por otra. Pero aún así son contados los programadores que REALMENTE entiendes en su máxima extensión est gran creación: las expresiones regulares.

Las expresiones regulares existen en todos los lenguajes de programación desde JAVA,c y C++ hasta el PHP,Phyton y Perl. En todos la sintaxis son muy similares exceptuando ciertos cambios en algunos caracteres.

En este tutorial vamos a ver un poco de las expresiones regulares y lo que podemos lograr con ellas, este es una breve introducción a este mundo.
Demilitador de las expresiones

Un delimitador es lo que marca el principio y el fin de una expresion regular. El delimitador que más comunmente se usa es la diagonal ‘/’:

m//;

Sin embargo este delimitador lo podemos cambiar por el que se nos pegue la gana, ya sea por una letra o algun otro símbolo:

#Delimitador !
m!expresion!;

#Delimitador =
m=expresion=;

#Delimitador –
m-expresion-;

El operador m//Este operador también conocido como de cotejo, se utiliza para localizar alguna expresión dentro de una cadena de texto o string. Si la expresión es verdadera entonces se regresará un 1.

La regla es sumamente sencilla, debes de usar el mismo delimitador para abrir y cerrar la expresión regular, y este debe de ser de un sólo caractér.
NOTA: A veces el uso de caracteres delimitadores como el + pueden hacer que tu código se difícil de leer.

Normalmente este operador es utilizado para verificar que nuestra variable tenga cierto valor. Por ejemplo:

my $string = «Mi frase no muy larga»;

if($string =~ m/frase/){
print «Se encontró la palabra: frase.\n»;
}

Al ver este pequeño pedazo de código verás un símbolo extraño «=~». Este símbolo le dice a perl que evalue la siguiente expresión regular a verdadero, lo que significa que si el operador regresa un valor de 1 o verdadero se imprimirá el texto dentro del «if».

Pero que pasa si quisieramos hacerlo al revés, si quisieramos checar que alguna expresión NO estuviera dentro de alguna cadena:

my $string = «Mi frase no muy larga»;

if($string !~ m/jugo/){
print «No se encontró la palabra: jugo.\n»;
}

Aquí vemos como debido a que NO se encontró la palabra «jugo» el código dentro del «if» es ejecutado.
El operador s///

Este operador que tambiés es conocido como operador de sustitución, es utilizado para sustituir alguna cadena o expresión por otra. Por ejemplo:

my $string = «Hoy es Lunes»;

$string =~ s/Lunes/Martes/;

Al correr la siguiente expresión el valor final de «$string» será de: «Hoy es Martes».

La sintáxis de este operador, es que primero va la cadena o expresión que queremos que sea sustituido seguido por lo que queremos sustituirlo con.

Otro ejemplo de esto es:
$string = «El nombre de mi perro es: (nombre)»;

$string =~ s/\(nombre\)/Rocky/;

Si corres esta expresión te imaginaras que el resultado va a ser: «El nombre de mi perro es: Rocky».
El operador tr///

También conocidmo como el operador de traducción nos sirve para cambiar carácteres individuales por otros. La diferencia que tienes con los otros operadores, es que este no lee variables dentro de la expresión.

my $string = «aparato»;

$string =~ tr/a/e/;

Al ejecutar este expresión el resultado va a ser: «eperete».
Opciones de los operadores

Si alguna ves has visto expresiones regulares anteriormente, quizá te habrás dado cuenta que al final de ellas luego hay letras. Estas letras son «opciones» que le indica a perl como interpretar la expresión.

Hay varias opciones que se pueden usar, pero como esto es sólo una introducción sólo voy a poner las más usuales:

Opcion: i Este operador le dice a perl que ignore el uso de mayúscula y minúsculas. Por ejemplo:

my $string = «Palabra»;

#La siguiente expresión da falso debido a que hay una mayúscula
print «Verdadero» if $string =~ m/palabra/;

#La siguiente expresión da verdadero debido a que le decimos a perl que no nos importan las mayúsculas
print «Verdadero» if $string =~ m/palabra/i;

Opción: g

Esta opción le dice a perl que repita la sustitución durante todas las ocurrencias de la cadena. Por ejemplo:

my $string = «Lunes y otro Lunes»;

#Solo hará el remplazo al primer Lunes
$string =~ s/Lunes/Martes/;

#Hará el remplazo al todos los Lunes
$string =~ s/Lunes/Martes/g;

Opción: m

Este opción le dice a perl que la cadena que se esta evaluando es de varias lineas. Para dar más velocidad al proceso, perl hace una optimización como si estuviera evaluando una sola linea. Así que si tu cadena tiene varios «\n», tienes que usar esta opcion para quitar esta optimización.
Meta-Secuencias

Dentro de nuestras expresiones podemos usar lo que se llaman «Meta-Secuencia», estos son caracteres que simbolizan cosas específicas y aquí esta una lista de las más usadas.

Meta: \b

Esta meta-secuencia se usa para marcar un fin de palabra. Por ejemplo:

$string = «Mi palabara es esta.»;

#Debido a que en esta expresión se usar el fin de palabra el resultado es verdadero por «es» y no por «esta».
print «OK» if $string =~ «\bes\b»;

Meta: \B

El contrario de la meta-secuencia anterior, esto simboliza un fin de no-palabra.

Meta: \d

Cualquier dígito (0-9). Por ejemplo:
my $string = «Numeros 12345»;

Cualquier espacio en blanco. Por ejemplo:
my $string = «Mis palabras»;

print «Hay números.» if $string =~ m/\d/;

Meta: \D

Simboliza cualquier no-digito.

Meta: \s

#Quitamos todos los espacios en blanco
$string =~ s/\s//g;

Meta: \S

Cualquier no-espacio.

Meta: \t

Cualquier tabulador.

Meta: \u

Cambia el siguiente carácter a mayúscula.

Meta: \U

Cambia los carácteres que siguen a mayúscula hasta encontrar un \E.

Meta: \l

Cambia el caracter que sigue por minúscula.

Meta: \L

Cambia los caracteres siguientes a minúsculas hasta encontrar un \E.

Meta: \w

Meta-secuencia para todos los caracteres de palabra, es decir todos los caracteres alfa-númericos y el guíon. Por ejemplo:
$string = ‘$%&·’;

print «No hay palabras» if $string !~ m/\w/;

Meta: \W

Todos los caracteres de no-palabra.
Notas Finales

Con este tutorial ya hechamos un vistazo muy amplio al mundo de las expresiones regulares, aunque aún faltan varios temas para poder manejar totalmente las expresiones regulares, pero ya será tema de otro tutorial.