Esteganografía visual

Ya expliqué en qué consistía la esteganografía en uno de mis artículos anteriores. En aquel caso exploramos el arte de ocultar información en el tráfico usual de una red, pero esta no es sino una modalidad muy reciente del arcano arte de ocultar información entre lo cotidiano. Hasta llegar a ese punto, la esteganografía se enfocó a ocultar sus mensajes a los ojos de los demás... burlar a sus oídos y ya no digo a sus sniffers vendría mucho después.

En uno de mis próximos artículos trataré la esteganografía sonora, pero en este nos enfocaremos en la visual.

Ejemplos artísticos de mensajes ocultos a la vista hay muchos. A veces se jugaba con la perspectiva, como en el cuadro de Holbein "Los embajadores" que visto de frente es un retrato habitual en el que sólo llama la atención una mancha bastante rara entre los protagonistas.


Mirando el cuadro en el ángulo correcto, aparece una calavera (aproximadamente desde abajo y a la izquierda ya que el cuadro estaba pensado para ponerse en la pared de una escalinata curva interior):


En este caso se usó una técnica de perspectiva denominada anamorfosis para ocultar el mensaje del artista de que por mucho que el hombre se ilustre y estudie su mundo (simbolizado ello en los instrumentos de la mesa), la muerte siempre está presente y se cobrará su tributo (la calavera).

El historiador griego Herodoto citaba un par de ejemplos tempranos de esteganografía utilizada por los griegos para ocultar mensajes en los que se describían los planes persas de invasión. Uno de esos ejemplos describía como un griego tatuó el mensaje secreto de alerta en la cabeza rapada de uno de sus esclavos, dejó que le volviese a crecer el pelo y lo envió de camino a Grecia para avisar. Teniendo en cuenta lo que tarda el pelo en volver a crecer lo suficiente y el tiempo que implicaba cualquier tipo de viaje en aquella época o bien el mensaje no era tan urgente o es sencillamente una patraña. Otro ejemplo, más verosimil, es el que relata como el espía grababa el mensaje en una tablilla de cera sin ella y luego tapaba el mensaje añadiendola. Luego podía escribir un mensaje inofensivo en la cera de la tablilla para engañar cualquier inspección. Para acceder al mensaje sólo era necesario derretir la cera.

En tiempos más modernos es bastante habitual ver películas de espías que dejan mensajes en espejos cubiertos de vaho. Al desaparecer este, el mensaje se vuelve invisible pero puede visualizarse de nuevo abriendo el grifo de agua caliente y dejando que el vaho cubra de nuevo el cristal.

Todos estos son ejemplos de esteganografía visual. Hay muchos más, tantos como técnicas inventadas por el hombre. Nosotros nos fijaremos en una muy utilizada en informática. Esta técnica explota paradójicamente una de las habilidades en las que los seres humanos son superiores a las máquinas: la capacidad de aproximación. El cerebro humano carece de la precisión de los ordenadores, pero sin embargo es capaz de extraer conclusiones a partir de aproximaciones en las que se conjugan los datos captados y la experiencia previa. Esto, que un niño de tres años ya hace inconscientemente, es desde hace años el campo de batalla diario de los estudiosos de la Inteligencia Artificial. Aplicado al campo de las imágenes esta habilidad nos permite distinguir objetos a pesar de que estos se encuentren deformados o borrosos. Un ejemplo son los habituales captchas que retan a los usuarios a leer unos carácteres intencionadamente d eteriorados con el fin de asegurarse de que el "usuario" es una persona y no un programa de ordenador.

Sin embargo, cuando se trata de detectar detalles esta capacidad de aproximación juega en nuestra contra a no ser que ya estemos alerta. Si no estamos avisados de antemano o especialmente entrenados, lo normal es que veamos una forma, la interpretemos y si deducimos lo que significa facilmente pasemos a otra cosa ignorando los detalles. Un ejemplo de este fenómeno lo tenemos diariamente en los periódicos en el juego de encontrar las 7 diferencias. A no ser que seamos aficionados a ese juego lo normal es que no encontremos ninguna diferencia en el primer vistazo. Sin embargo las diferencias están ahí y no son sino información oculta en una imagen.

Nosotros explotaremos esto jugando con los colores de una imagen. Mientras que los ordenadores son capaces de distinguir con precisión un color de otro parecido en una paleta de miles de colores, lo cierto es que los seres humanos frecuentemente no somos capaces de distinguir dicha dife rencia sobre todo si la superficie de cada uno de los colores es muy reducida. ¿Seríamos capaces de distinguir si un pixel morado es exactamente igual de morado que el pixel que tiene a su lado?, la respuesta es que no, sobre todo si la diferencia es pequeña.

Los ordenadores actuales pueden mostrar en pantalla paletas de miles de colores. Para mostrar cada color, el ordenador le asigna un número identificativo de manera que los programas sólo tengan que usar ese número para decirle a la tarjeta gráfica que muestre ese color. Los colores similares tienen números correlativos así que si los visualizásemos consecutivamente veríamos gradientes de color en vez de cambios bruscos. Pongamos, por ejemplo, que una tarjeta gráfica pudiese mostrar imágenes en color verdadero lo que supondría que sería capaz de poner 16.777.216 colores diferentes en pantalla. Para ello cada color debería tener un número identificativo de 24 bits (2^24=16.777.216). Si jugásemos con el bit menos significativo (el de más a la derecha) del número identificativo para codificar información el usuario sería incapaz de notarlo ya que los colores resultantes serían tan parecidos que sería muy difícil distinguirlos entre si.

Así que eso será lo que hagamos, cogeremos una imagen y la recorreremos manipulando el bit menos significativo d e cada pixel de manera que ese bit corresponda a un bit del mensaje que queremos ocultar en la imagen.

Para ilustrarlo he escripto un pequeño programa en Python capaz de esconder un texto en una imagen que tenga formato BMP o PNG. El programa se puede descargar de google code y para ejecutarlo hace falta tener instalada la Python Imaging Library (PIL). En Ubuntu se puede instalar PIL mediante un sencillo comando:

[...]/stegimage$ sudo aptitude install python-imaging

Hecho lo anterior ya podemos ejecutar el programa desde la carpeta donde lo hayamos descomprimido. En dicha carpeta contamos con una imagen que hará de anfitrión de los datos a ocultar (lena_std.png) y el texto a ocultar (texto_a_ocultar.txt ;-) ). Se puede usar cualquier imagen PNG y cualquier texto pero hay que tener en cuenta que se tienen que cumplir determinadas relacio nes entre el tamaño de la imagen y el texto a ocultar, tal y como veremos al estudiar el código del programa. Para no complicarse la vida en la primera prueba lo mejor es usar los archivos de ejemplo que vienen junto al programa. Para ver los parámetros que acepta el programa no hay más que teclear su nombre sin ninguna opción:

/stegimage$ ./stegimage.py
Stegimage
===========

Programmed by: Dante Signal31

Written for experimental purpuses.

This program hides data in image files.

Format ./stegimage.py
-i ----------> image file to use for hiding.
-d -----------> Data file to hide in image file

-o ---------> Output image file with data file hidden inside.
-x ------------> Extract data file (set with -d) from steg file.

-s ------------> S ets how many bits we should hide in each selected pixel (DEFAULT=1)
-h | --help --------------> Print this text.


Examples:
Hiding a file:./stegimage.py -i image_file.bmp -d hidden.txt -o image_steg_file.bmp
Extracting a file:./stegimage.py -x image_steg_file.bmp -d hidden.txt

Siguiendo las indicaciones de la ayuda teclearemos lo siguiente para ocultar el texto de ejemplo (que dicho sea de apaso es un copy-paste de la excelente obra sobre el cifrado en la Segunda Guerra Mundial que Ramón Ceano publicó en Kriptópolis):

/stegimage$ ./stegimage.py -i lena_std.png -d texto_a_ocultar.txt -o lena_steg.png

Como podemos comprobar se ha generado una nueva imagen (lena_steg.png) que es la que oculta el texto secreto. Visualmente las dos son idénticas (para un humano), la primera es la imagen original y la segunda la que contiene el mensaje:




Para extraer el mensaje oculto no tenemos más que hacer lo siguiente:

/stegimage$ ./stegimage.py -d texto_extraido.txt -x lena_steg.png

Ahora estudiaremos el código del programa para entender bien cómo funciona esta técnica de ocultación. Haré un repaso puntual del código, pero habrá fragmentos de este que no plasmaré aquí porque no tienen mayor complicación así que recomiendo que el lector repase el código en su totalidad por su cuenta (no debería resultarle difícil porque he procurado comentarlo bastante y es bastante corto).

La función que se encarga de esconder los datos en la imagen es hideFile a la que se le pasan como parámetro dichos datos (en nuestro ejemplo el texto a esconder):

def hideFile(self, data_file_name):
""" This function encodes data file into image host file."""
self.data_file_size = (os.stat(data_file_name))[stat.ST_SIZE]
self.calculateSeparation(self.getDataFileSize())
self.data_file = open(data_file_name, 'rb')
if (self.getSeparation() < 0): #This means that data file is too big.
return ERROR
else:
self.encodeHeader()
self.byte=self.data_file.read(1)
self.bytes_written = 0
while (self.byte):
self.byte_in_bits = libmymath.int2bin(n=ord(self.byte), count=8)
self.encodeBits(self.byte_in_bits)
self.byte = self.data_file.read(1)
self.bytes_written = self.bytes_written + 1
self.percentage_done = /
int
((float(self.bytes_written) / float(self.data_file_size)) * 100)
print str(self.percentage_done) + "% : " + str(self.byte_in_bits)
self.hostFileImage.save(self.hostFileName)
self.data_file.close()
return OK

Como se puede ver, esta función averigua el tamaño de los datos que queremos ocultar y posteriormente en la llamada a encodeHeader usará los primeros píxeles de la imagen para codificar en ellos el tamaño de los datos ocultados. En principio mi script cuenta con una constante HEADER_SIZE que fija 32 bits para codificar el tamaño de los datos ocultados por lo que los primeros 32 pixels consecutivos de la imagen tendrán sus bits menos significativos modificados (siempre y cuando STEP=1, como se explicará seguidamente). El número de bits que se modifican por pixels lo fija la constante STEP del fichero stegimage.py aunque el usuario la puede modificar usando el parámetro "-s" en la llamada al programa. En principio STEP está fijado a 1 de manera que sólo se modifica 1 bit por pixel tocado, esto significa que si queremos ocultar un byte de datos (8 bits) tendremos que modificar el valor del bit menos significativo de hasta 8 pixels para que dicho bit corresponda con el respectivo del byte a ocultar. Para recomponer el byte ocultado tendremos que mirar el bit menos significativo de cada uno de los 8 pixels e ir recomponiendo el byte original. Esto tiene una limitación y es que con un STEP=1 sólo podremos ocultar ficheros cuyo tamaño en bits no supere al número de pixel de la imagen tras restar los 32 pixels que consume el codificado de la cabecera. Para superar esta limitación, y ocultar textos o ficheros más extensos, se puede aumentar el valor de STEP para ocultar más bits del mensaje en cada pixel de la imagen pero en ese caso hay que tener en cuenta que la variación de color entre el pixel modificado y sus vecinos es más brusca y la anomalía será más fácilmente detectable, como se puede ver en la imagen de ejemplo siguiente en la que se ocultó el mismo texto que antes con un STEP=16 (fíjese como ahora los pixel modificados sí son claramente detectables en la forma de esas líneas verticales de "ruido"):



Como también se puede ver en la imagen anterior, los bits modificados están equiespaciados para dificultar su detección al dispersar la anomalía generada. La separación entre pixels modificados se calcula con la llamada a calculateSeparation de hideFile en función del tamaño del mensaje a ocultar, el tamaño en pixels de la imagen contenedora y el STEP que hayamos fijado. Hay que tener en cuenta que si se ha usado un STEP diferente de 1 (el de por defecto) habrá que decírselo a stegimage.py a la hora de extraer el mensaje. Si no se hace así, el programa no sabrá en qué pixels fijarse para reconstruir el mensaje (o mejor dicho, usará un STEP=1 y mirará los pixels equivocados). Por ejemplo, si al codificar hubiésemos usado un STEP de 8, la orden de extracción sería la siguiente:

/stegimage$ ./stegimage.py -d texto_extraido.txt -x lena_steg.png -s 8


Una vez calculada la separación mediante calculateSeparation y grabada la cabecera en los primeros pixels mediante encodeHeader, la función hideFile comienza un bucle en el que va leyendo byte a byte el mensaje a ocultar y va grabando esos bytes en los pixels de la imagen mediante la función encodeBits:


def encodeBits(self, bit_string, position=0):
""" This function deals with writing of long bit strings."""
if (position == 0):
self.current_position = self.last_position
else:
self.current_position = position
# self.x = 0
for bit in bit_string:
self.setBit(self.current_position, bit, self.x)
if (self.x < self.step-1):#We store up to STEP data bit in every selected pixel.
self.x = self.x + 1
else:
self.x = 0
self.current_position = self.current_position + self.separation
self.last_position = self.current_position


La clave de la función anterior, la que realmente modifica el pixel es setBit:


def setBit(self, startPosition, value_string, offset=0):
""" To put a bit in a position. """
self.pos_y = int(libmymath.myround((startPosition / self.width), libmymath.DOWN))
self.pos_x = (startPosition % self.width)
self.original_value = self.pixmap[self.pos_x, self.pos_y]
self.binary_original_value_string = self.color2binary(self.original_value)
if (offset == 0):
self.binary_modified_value_string = /
self
.binary_original_value_string[:-(offset+1)] + value_string
else:
self.binary_modified_value_string = /
self
.binary_original_value_string[:-(offset+1)] + value_string + /
self
.binary_original_value_string[-offset:]
self.modified_value = self.binary2color(self.binary_modified_value_string)
self.pixmap[self.pos_x, self.pos_y] = self.modified_value


Una vez codificados todos los bytes del mensaje a ocultar en los pixels de la imagen, hideFunction guarda la imagen modificada en el fichero de salida que fijamos al llamar al programa mediante la función hostFileImage.Save.

Con esto queda explicado el esqueleto del proceso de ocultación de un mensaje en una imagen, el proceso de extracción para obtener de vuelta el mensaje es exactamente igual pero a la inversa. Para más detalle lo mejor es una lectura detenida del código fuente de stegimage.py y de sus librerías adjuntas. Creo que el código está lo suficientemente conciso y comentado como para asegurar una fácil comprensión.

Así damos fin a este artículo, en el que hemos repasado brevemente la historia y las bases del extensísimo campo de la esteganografía visual. Este campo está en constante movimiento, no sólo por su utilidad en el campo de la Inteligencia (con I mayúscula) sino también en el comercial, concretamente en el de la protección de derechos de autor ya que la esteganografía es un recurso excelente para firmar determinadas fotografías de manera que se puede controlar su difusión comercial.

Evitando las escuchas en redes conmutadas

En un artículo que publiqué en Diciembre hablé sobre distintas técnicas para realizar escuchas en redes conmutadas. Me quedó pendiente desarrollar qué opciones tenemos frente a este tipo de ataques.

Las ataques de ARP Spoofing, también llamados envenenamiento ARP, se basan en introducir información falsa en las tablas de ARP de uno (o ambos) de los de los extremos de una comunicación con el fin de que este utilice inadvertidamente al atacante como intermediario a la hora de trasnmitir y recibir información. Esto permite al atacante no sólo espiar la información intercambiada por el atacado, sino también modificarla a su antojo.

Para combatir con eficacia este tipo de amenazas, un ingeniero de seguridad debe ser consciente de las técnicas de prevención, detección y reacción que puede emplear contra ellas.

La principal técnica de prevención es un buen diseño de la red. Muchos ingenieros no se dan cuenta, pero poner PCs de usuario en redes de paso supone un verdadero riesgo ya que si alguno decidiese utilizar herramientas de ARP Spoofing podría interceptar no sólo el tráfico destinado y originado hacia/desde su segmento sino todo aquel que lo utilice como red de tránsito. Un diseño correcto puede limitar a un único segmento de red el daño que un atacante puede realizar mediante ARP Spoofing. La manera de evitar esto es mantener las redes intermedias de tránsito vacías de PCs de usuarios, concentrando a estos en segmentos localizados en las "hojas" de nuestra red.



A la izquierda de la figura anterior (no se por qué pero Blogger la saca muy borrosa, si quiere ver el original, mucho más definido, pulse sobre la imagen) se puede ver una red mal diseñada al permitir que la red de paso (B) contenga PCs de usuario. Cualquiera de estos PCs de usuario puede lanzar un ataque de ARP Spoofing para desviar el tráfico cursado entre el router interior y el exterior con el resultado de que podría espiar todo el tráfico saliente de la red A.
A la derecha de la figura anterior se encuentra un diseño correcto. En él, la red B se ha vaciado de PCs de usuario. Los PCs que antes estaban en B han pasado a una red "hoja", C. Gracias a este diseño, un atacante de la red C sólo podría escuchar el tráfico de su red pero no de la B.

Este buen diseño sobre el papel debe desplegarse en la práctica de manera correcta. Si a pesar de haber vaciado de PCs las redes de tránsito, un intruso puede pinchar un portátil a una de estas redes seremos igual de vulnerables que antes. Para evitarlo hay que tomar medidas preventivas en los niveles de la capa OSI 2 y 1 (enlace y físico):

  • En la capa 2 hay que segmentar los conmutadores que dan servicio a las distintas redes en VLANs separadas asignando a cada VLAN única y exclusivamente los puertos dedicados a cada uno de los equipos residentes en ellas. Muchos administradores dejan puertos libres en cada VLAN por si un día se necesita pinchar urgentemente un equipo a ellas sin tener que esperar a que el administrador lo configure en el conmutador; esa comodidad tiene su contrapartida negativa y es que se deja abierta una puerta a nuestra red, puerta que puede aprovechar un atacante para pinchar su equipo a nuestra red si consigue acceso físico al conmutador (cosa no demasiado difícil en algunas organizaciones). Además, los puertos en uso de las redes de tránsito deben protegerse de alguna manera para evitar que máquinas no autorizadas se conecten a ellas. Lo ideal sería desplegar una solución del tipo NAC o 801.1X, pero la mayor parte de las redes actuales carece por ahora de la infraestructura necesaria para algo tan complejo. Al menos, lo que sí se puede hacer es limitar el uso de esos puertos concretos del conmutador a las MACs concretas de los equipos legítimos. No es una solución definitiva porque es muy fácil falsificar la MAC de un equipo, pero al menos servirá para retrasar al atacante y, con suerte, generará algún log de error en el equipo que servirá para alertar a los administradores si estos cuentan con una infraestructura de correlación de logs adecuada (del tipo Cisco Mars, Bitácora, logICA, etc). Por último, habrá que configurar los conmutadores correctamente para evitar que se utilicen contra ellos algunas de las VLAN Hopping existentes para acceder a una VLAN desde un puerto perteneciente a otra diferente.
  • En la capa 1 las medidas de seguridad son evidentes y se corresponden, al fin y al cabo, con las medidas de seguridad habitualmente recomendadas para las instalaciones de comunicaciones y tratamiento de datos. Básicamente se trata de impedir que una persona no autorizada pueda interactuar físicamente con alguno de nuestros conmutadores, por ejemplo pinchando su portátil a una VLAN no autorizada, apagando el conmutador para forzar una redirección del tráfico, o accediendo al puerto de consola del conmutador para reconfigurarlo. Para ello, el equipamiento de comunicaciones debe situarse en armarios cerrados con llave y preferiblemente vigilados con un circuito cerrado de cámaras, en salas de acceso restringido y con un soporte eléctrico y climático controlado y a prueba de fallos.
También está la opción de desplegar infraestructuras especializadas en combatir este tipo de ataques. Tal es el caso de algunas propuestas de código abierto enfocadas a integrar en la red un servidor dedicado a responder a las peticiones ARP a partir de una tabla centralizada con todas las correspondencias IP-MAC de la red, de manera que los conmutadores bloquearían todas las respuestas ARP (incluidas las utilizadas por el atacante para envenenar las tablas de ARP) excepto los originadas desde el puerto de este servidor. El problema de esta opción es la complejidad al no existir herramientas ya desarrolladas que implementen estos mecanismos y depender de las soluciones artesanales que se programe cada uno.

Para seguir el resto de las explicaciones le recomiendo que descargue y experimente con la maqueta de Netkit que he utilizado para escribir este artículo, es similar a la que se usó de ejemplo en los artículos "Creación de laboratorios virtuales con Netkit" I y II (lea estos artículos si no sabe como utlizar una maqueta realizada con Netkit) pero le he añadido una red de gestión, de manera que tenga una puerta trasera para acceder a los equipos por SSH sin mezclarse con el tráfico de la red de pruebas.

En el escenario de ejemplo, Alice quiere navegar por internet a través de un conmutador y un enrutador que le sirve de puerta de enlace; y PC-Sniffer quiere espiar el tráfico que Alice intercambia con Internet.

Teniendo en cuenta lo anterior y a partir de ahora, el esquema de la red de pruebas que vamos a utilizar en este artículo es el siguiente:




En lo que se refiere a las técnicas de detección, la vigilancia de los paquetes intercambiados en la red y de las tablas de ARP de los equipos clave serán nuestras principales armas.

Vigilando el tráfico de red se pueden detectar anomalías que nos alerten del trascurso de un ataque de ARP Spoofing. Examinando con Wireshark capturas del tráfico cursado a través del Switch de la maqueta podemos ver las siguientes anomalías:
  • En la captura del ataque con Ettercap podemos ver (paquetes 1 a 4) como el PC Sniffer (192.168.0.3) pregunta a la red por la MAC del Router (192.168.0.1) y por la de Alice (192.168.0.2). En los paquetes 5 y 6 ya aparecen las primeras señales de alerta; aparentemente el Router y Alice se lanzan pings entre sí, pero si examinamos la MAC de origen de ambos ping podemos ver que ¡en realidad se trata la MAC del PC-Sniffer!. Inmediatamente después, y sin esperar respuesta a los ping, el PC Sniffer manda actualizaciones de ARP para "envenenar" las tablas de Alice y el Router (paquetes 7 y 9). El resultado es que las respuestas a los pings le llegan al PC-Sniffer, lo que le permite saber que su ataque ha tenido éxito. En los paquetes 15 y 16 se puede ver como las respuestas a los pings se reenvían a sus legítimos destinarios, tal y como se hará con el resto del tráfico una vez que el PC-Sniffer lo haya visualizado. A partir de ahí (paquetes 19 a 26) se puede ver como el PC-Sniffer insiste machaconamente en enviar paquetes de actualización ARP para mantener las tablas de Alice y del Router "correctamente envenenadas". Si todo lo anterior ya debería inquietarnos, es cuando Alice comienza a navegar cuando vemos que algo va definitivamente mal. Porque a partir del paquete 43 vemos que todo el tráfico parece duplicado. Esto se debe a que el tráfico tiene que atravesar el Switch una vez, de camino al PC-Sniffer, y otra, de camino a su destinatario, en vez de atravesar el Switch una única vez (que sería lo lógico). De hecho, al mismo Wireshark le parece rara la situación y a partir del paquete 48 comienza a colorear de negro los paquetes repetidos para alertar de que algo no va nada bien.
  • Por su parte, en la captura del ataque realizado con Arppoison (incluido en la carpeta /root/scripts del PC-Sniffer de la maqueta), se pueden observar comportamientos anómalos. Arpoison es una herramienta programada con fines didácticos, así que su funcionamiento es algo más primitivo que el de Ettercap. Para empezar no hace un ping previo para comprobar que el envenenamiento se ha realizado con éxito y luego produce las mismas anomalías en los paquetes intercambiados e incluso alguna más. Y es que, cuando se usa Arpoison, se puede ver como en las capturas realizadas en el Switch aparece paquetes de ICMP Redirect (el primero aparece en el paquete 12), tan raros en las redes modernas que el Wireshark lo colorea de negro para señalarlo como anomalía. Esto se debe a que Arpoison utiliza Scapy para manejar paquetes y este a su vez Libpcap para realizar las escuchas. el problema es que Libpcap saca copias de los paquetes recibidos y se las entrega a las aplicaciones de usuario, pero no impide que los paquetes originales sigan siendo procesados por el kernel del PC. El kernel del PC-Sniffer no sabe nada de las aviesas intenciones de su dueño por lo que reacciona automáticamente cuando recibe un paquete que no está dirigido a su dirección IP enviando un paquete de ICMP Redirect alertando al remitente de que esos paquetes no le corresponden. Esta anomalía es tan evidente que cualquier IDS/IPS, por malo que fuese, lo habría detectado; para evitarla el dueño del PC-Sniffer podría haber activado su cortafuegos local para bloquear con él todos los paquetes ICMP salientes (si su cortafuegos le permite afinar bastaría con bloquear los paquetes ICMP Redirect salientes).

A nivel local, las inconsistencias en las tablas de ARP son síntomas muy serios de un posible ataque. Generalmente, es muy difícil que un PC y el enrutador que hace de puerta de enlace de la red tengan la misma MAC por lo que cuando esto ocurra deberían encenderse nuestras alarmas. Otra anomalía que debería ponernos en alerta es el cambio de la MAC conocida de equipos clave de la red, como por ejemplo los enrutadores que hacen de puerta de enlace.

En estado normal, la tabla de ARP de Alice tiene el siguiente aspecto:

PC-Alice:~# arp -i eth0 -a
? (192.168.0.1) at EA:0E:85:D7:58:04 [ether] on eth0


Si el atacante (PC-Sniffer) iniciase un ataque con Ettercap:

PC-Sniffer:~# ettercap -M arp:remote -T /192.168.0.1/ /192.168.0.2/

ettercap NG-0.7.3 copyright 2001-2004 ALoR & NaGA

Listening on eth0... (Ethernet)

eth0 -> CA:88:E3:51:83:57 192.168.0.3 255.255.255.0

SSL dissection needs a valid 'redir_command_on' script in the etter.conf file
Privileges dropped to UID 65534 GID 65534...

28 plugins
39 protocol dissectors
53 ports monitored
7587 mac vendor fingerprint
1698 tcp OS fingerprint
2183 known services

Scanning for merged targets (2 hosts)...

* |==================================================>| 100.00 %

2 hosts added to the hosts list...

ARP poisoning victims:

GROUP 1 : 192.168.0.1 EA:0E:85:D7:58:04

GROUP 2 : 192.168.0.2 BA:4E:E3:B8:96:91
Starting Unified sniffing...


Text only Interface activated...
Hit 'h' for inline help



Sat Mar 14 10:59:44 2009
TCP 192.168.10.1:49581 --> 192.168.0.2:22 | AP

...`..........I.S.4S..o^...D./~.....u.i....K...gaK5J

El resultado sobre la tabla de ARP de Alice sería el siguiente:

PC-Alice:~# arp -i eth0 -a
? (192.168.0.1) at CA:88:E3:51:83:57 [ether] on eth0
? (192.168.0.3) at CA:88:E3:51:83:57 [ether] on eth0

Como se puede ver, desde el punto de vista de Alice, no sólo ha cambiado la MAC del enrutador (192.168.0.1) sino que además ahora parece coincidir con la MAC de un PC (192.168.0.3), lo que es señal inequívoca de que se está produciendo un ataque de ARP Spoofing que intenta desviar el tráfico de Alice destinado al enrutador hacia un PC intruso. Cuando este PC finaliza Ettercap, este se encarga de restablecer las tablas de ARP a su estado correcto. Lo que deja a Alice de la siguiente manera:

PC-Alice:~# arp -i eth0 -a
? (192.168.0.1) at EA:0E:85:D7:58:04 [ether] on eth0
? (192.168.0.3) at CA:88:E3:51:83:57 [ether] on eth0

Como se puede ver, el ataque deja huellas tanto durante su transcurso como durante un corto tiempo tras él (hasta la expiración de la entrada en la tabla de ARP). Esto se debe a que el intruso debe interactuar con sus víctimas, antes de iniciar el ataque, para recopilar las MACs de dichos equipos con el fin de reparar las tablas de ARP tras él. Se puede estudiar la estructura interna de un programa similar a Ettercap en el mencionado artículo sobre escuchas en redes conmutadas. En ese programa, el Arpoison mencionado antes, la función que deja la huella "incriminatoria" en las tablas de ARP es la función gatherData(), ejecutada antes del ataque mismo. Como esta función debe preguntar a Alice y al Router por sus MAC mediante una llamada de ARP (representada en el código fuente del artículo por la llamada a la función scapy.getmacbyip() dentro de gatherData()), es el momento en el que el atacante PC-Sniffer "toca" directamente a sus víctimas dejando las huellas mencionadas. Se podría plantear la pregunta de si el atacante podría renunciar a ejecutar esta función para minimizar su huella, pero lo cierto es que no, porque si no averigua las MACs originales de los equipos a espiar no podrá lanzar el ataque ni reconstruir las tablas de ARP tras él.

Visto lo anterior, es evidente que son necesarias herramientas automatizadas que nos permitan defender las tablas de ARP de los equipos críticos que queramos salvaguardar de este tipo de ataques.

Una de las herramientas clásicas a este respecto es Arpwatch. Esta herramienta monitoriza la tabla de ARP y alerta por correo electrónico al administrador cuando se produce el cambio de una correspondencia IP-MAC. Lo ideal es instalar dicha herramienta en todas las estaciones de trabajo Linux de la red. En redes con direccionamiento estático, si se tiene la certeza de que no se ha producido el recambio de la tarjeta de red de ningún ordenador, la llegada de un correo de Arpwatch suele ser alerta inequívoca de que se está produciendo un ataque de ARP Spoofing. En redes con direccionamiento dinámico (DHCP), los pares IP-MAC cambian con cierta frecuencia, por lo que puede ser complicado monitorizar todos los cambios, aunque lo que sí se puede vigilar es el registro IP-MAC de la puerta de enlace por defecto de cada red, la cual debería permanecer inalterable en las tablas de ARP de todas las estaciones de trabajo.

Otra opción, algo más compleja pero con más posibilidades es ArpON. A diferencia de Arpwatch, ArpON no se limita a alertar al administrador sino que reacciona para bloquear el ataque. ArpON tiene dos modos de funcionamiento, estático y dinámico. En modo estático (SARPI), ArpON toma nota al arrancar de las entradas de la tabla de ARP, guardando esta información en una caché alternativa. A partir de ahí, ArpON sólo permite que se tramiten las peticiones y respuestas ARP de pares IP-MAC que no entren en contradicción con la información previa de su caché. El modo dinámico (DARPI) es similar, pero permite que la caché de ArpON vaya incorporando nuevos pares IP-MAC desconocidos en el momento de su arranque.

En redes con DHCP se puede optar también por activar un sistema de DHCP Snooping. Aparte de evitar que aparezcan servidores DHCP "furtivos", este sistema mantiene un registro de las MACs asociadas a las IPs concedidas y los puertos de los conmutadores donde se encuentran estas MACs. Con esta información, el sistema monitoriza los intercambios de ARP que se producen en sus puertos y si detecta un paquete ARP cuyo origen a nivel IP no se corresponde con la MAC registrada lo bloquea para impedir el envenenamiento. Esta opción se encuentra ampliamente disponible, por ejemplo en los equipos de Cisco donde recibe el nombre de Dynamic ARP Inspection.

Las Crypto Guerras


Las Crypto Wars o Crypto Guerras es como se conoce al conflicto desarrollado desde los años 70 entre los gobiernos y los grupos de defensa de las libertades civiles acerca del uso de técnicas criptográficas por los particulares.

Todo comenzó cuando en los años 70 el gobierno americano empezó a darle a la comercialización y exportación del software y de los algoritmos criptográficos un tratamiento equivalente al del armamento. La medida se situaba dentro del contexto del punto más crudo de la Guerra Fría, cuando la Inteligencia de ambos lados del Telón de Acero movilizaba ingentes recursos humanos, económicos y materiales para averiguar lo que sabía el enemigo y, a la vez, evitar que este hiciese lo mismo.

Por tanto, resultaba crucial reforzar la criptografía que protegía la información gubernamental. Pero a la vez, había que asegurarse de que en caso de que se produjese una fuga de información o una conjura interna esta podría ser detectada por los servicios de contrainteligencia por lo que había que evitar la difusión de una criptografía fuerte entre los particulares. Esta dicotomía de intereses es la razón de la profunda implicación de los gobiernos, a través de Agencias y de los departamentos de Defensa, en la investigación y el desarrollo de técnicas criptográficas con el fin de ajustar dichos desarrollos a sus intereses concretos y controlar en lo posible su difusión a los ciudadanos.

Dado que es muy difícil mantener en secreto un algoritmo criptográfico, los gobiernos han optado por tres vías de control:

  • Prohibir el uso de técnicas criptográficas.
  • Limitar la longitud de las claves utilizadas a un valor demasiado difícil de romper por un particular pero vulnerable a los sistemas informáticos gubernamentales.
  • Obligar al uso de sistemas y algoritmos con una puerta trasera (en la literatura anglosajona red thread) accesible por el Gobierno para descifrar el tráfico.
El uso de la primera vía ("prohibir el uso de técnicas criptográficas") apenas se da en la actualidad. Al principio, este control no fue demasiado difícil ya que la informática que se daba fuera del sector militar y universitario era muy escasa. El sector militar siempre ha obedecido órdenes y el universitario recibe importantes subvenciones del militar por lo que en general se ajustó a las restricciones gubernamentales. Los problemas comenzaron a surgir cuando los hogares empezaron a adquirir ordenadores, y más importante: a unirlos a través de Internet. En ese momento empieza a cobrar fuerza la reivindicación de los ciudadanos de asegurar la confidencialidad de sus datos mediante cifrado. Además, esas reivindicaciones no tardaron en ser apoyadas por sectores económicos que veían en Internet un medio para establecer nuevas vías de negocio que debían ser lógicamente protegidas mediante cifrado. Toda esa presión conjunta ha obligado a la mayor parte de los gobiernos a aceptar el uso de técnicas criptográficas por parte de los ciudadanos.

Un ejemplo de la segunda vía ("limitar la longitud de las claves utilizadas") se dió en la definición del algoritmo DES. En los años 70, aún se utilizaban cifradores mecanicos de tipo rotor (meras evoluciones del clásico Enigma alemán). La Agencia de Seguridad Nacional (NSA) estadounidense podía descifrar sin problemas este tipo de tráfico. Sin embargo el sector bancario presionaba para obtener un algoritmo de cifrado moderno que permitiese asegurar sus transmisiones de datos. La NSA temía perder el control que tenía sobre las comunicaciones si se generalizaba el uso de un algoritmo realmente potente por lo que se involucró directamente en el diseño del DES. Hay dos elementos que fueron duramente criticados del DES: por un lado, el fuerte secretismo que había en torno a la cajas-S en las que se basaba el algoritmo, y por otro, la escasa longitud de clave elegida (56 bits). Pronto se extendió el rumor de que la ocultación del diseño de las cajas-S se debía a que la NSA había instalado en ellas puertas traseras y que la longitud de la clave se había elegido corta a adrede para que los sistemas de la NSA pudiesen realizar ataques de fuerza bruta para descifrarlo. Un par de décadas más tarde parece demostrado que ambos rumores eran infundados, las cajas-S no tenían puerta trasera y la NSA carecía en ese momento del equipamiento necesario para tumbar por fuerza bruta un texto cifrado con DES (lo consiguió unos años más tarde). Lo que sí parece que ocurrió es que la NSA difundió intencionadamente ese rumor para extender la creencia de que el DES era inseguro lo que evitó su adopción por parte de gobiernos extranjeros, los cuales que siguieron utilizando máquinas de rotores... a las que la NSA pudo seguir espiando sin problemas.
Cuando el uso de los nuevos algoritmos de cifrado comenzó a generalizarse, el gobierno de los EEUU optó por prohibir la exportación de cualquier producto que incluyese procesos criptográficos que utilizasen claves de longitud superior a los 40 bits, incluyendo además este tipo de exportaciones en la categoría de armamento y materiales peligrosos para la seguridad nacional.

La tercera vía se basa en la premisa de que cualquiera que encripte datos debería darle al gobierno una copia de la clave utilizada para el cifrado, de manera que las agencias de inteligencia gubernamentales puedan descifrar el tráfico si lo consideran necesario. Un ejemplo de este enfoque se dió en 1993 cuando la administración de Bill Clinton propuso un estándar, denominado Clipper Chip, para sustituir al DES. Este estándar se basaba en un chip criptográfico que utilizaba un algoritmo clasificado, y por tanto no sujeto a una revisión pública, denominado Skipjack. Este algoritmo permitía que las agencias gubernamentales pudiesen escuchar las transmisiones cifradas con el chip. La idea del gobierno era incentivar el uso de este chip entre los fabricantes de telefonía y equipos de telecomunicaciones. Sin embargo, la idea no llegó a buen puerto porque el carácter secreto del algoritmo despertó la desconfianza de los fabricantes (que luego se vió justificada al descubrirse varias vulnerabilidades en el estándar) y además la libre circulación por Internet de otras soluciones de cifrado fuerte como PGP, Nautilus y PGPfone dejaba en clara desventaja al Clipper Chip. En 1996 ya era innegable el fracaso de esta iniciativa y de otras similares ante la dificultad de crear la figura de un tercero de confianza que almacenase una copia de las claves de forma segura y que no se prestase a abusos.

Las respuestas a estas iniciativas gubernamentales por parte de los adalides de las libertades civiles han sido variadas. La creación del PGP, en 1991, puso por primera vez la criptografía asimétrica a disposición del gran público convirtiéndose en una herramienta imprescindible para las organizaciones de defensa de los derechos civiles, sobre todo en países no democráticos. Paradójicamente, su creador, Phil Zimmermann, fue procesado por tráfico de armas debido a que el PGP usaba claves de 128 bits, lo que estaba muy por encima del limite de 40 bits que fijaba la ley estadounidense sobre venta de armas, que, como mencionaba antes, integraba la exportación de algoritmos criptográficos. Sin embargo, Zimmermann había sido considerablemente astuto y había exportado PGP de una manera bastante inusual. Había imprimido el código fuente en libros editados por la editorial del MIT y eran estos los que se habían exportado fuera de los Estados Unidos. Los programadores extranjeros sólo habían tenido que arrancar las cubiertas del libro y pasar sus hojas por un escáner OCR, para obtener el código fuente en formato digital y listo para compilarlo con GCC. Finalmente, los juzgados tuvieron que dejar en libertad a Zimmermann, libre de cargos, ya que aunque la exportación de software criptográfico estaba regulada por ley, la exportación de libros está sin embargo protegida por la Primera Enmienda, de rango constitucional (y por tanto superior), que defiende la libertad de expresión y de prensa.

Tras el caso Zimmermann se hizo evidente que no se podían poner puertas al campo y se relajaron los controles, de tal manera que ya sólo está prohibida la exportación de software criptográfico a los países de la lista negra de los Estados Unidos (Irán, Corea del Norte, etc).

El problema del terrorismo internacional ha devuelto a la vida el debate acerca de la necesidad de monitorizar el tráfico de voz y datos con el fin de cazar a los terroristas. El hecho de que gran parte de las infraestructuras de comunicaciones actuales se construyeran durante la vorágine de las puntocom es la causa de que estas no se diseñasen con criptografía integrada, lo que las hubiera encarecido considerablemente y alargado sus plazos de despliegue. Esta carencia de criptografía integrada en las redes de comunicaciones facilita la labor inspectora de las agencias gubernamentales.

Pero hoy en día está claro que el mercado tiende cada vez más hacia las transacciones electrónicas, y estas deben ser protegidas mediante cifrado, razón por la que el conjunto de la industria tiende a dotar (ahora sí) a sus nuevos sistemas de sistemas de cifrado integrado (por ejemplo: Skype).

Ante esta situación, y dado que el dinero manda, resulta cada vez más evidente que este se inclina por el lado del libre uso de la criptografía, lo que supone la victoria en las Crypto Guerras de los defensores de los derechos civiles.