Archivo

Posts Tagged ‘python stem tor’

Creando sitios ocultos en TOR de forma programática con TxTorCon

diciembre 4, 2014 1 comentario

Anteriormente he hablado sobre el uso de Stem para controlar instancias de TOR, una potente librería que no solamente se aprovecha del protocolo de control de TOR para la administración remota de una instancia en ejecución, sino que también cuenta con algunas utilidades para arrancar una nueva instancia con configuración personalizada, descargar y parsear los descriptores emitidos por las autoridades de directorio, entre muchas otras funcionalidades útiles. Es una librería que se explota bastante bien en Tortazo, una de las herramientas que he escrito para realizar pruebas de penetración contra repetidores de salida y servicios ocultos en la red de TOR.
Aunque Stem es una librería muy potente, existen otras alternativas que cuentan con las mismas capacidades y en esta ocasión, voy a hablar sobre TXTORCON.

¿Por qué TxTorCon? Porqué se trata de una implementación del protocolo de control de TOR basada en Twisted y a diferencia de Stem, TxTorCon es una implementación asíncrona. Una librería como TxTorCon permitirá crear programas reactivos que se encargarán de ejecutar acciones sobre una o varias instancias de TOR ante una lista de eventos predefinidos.

En esta entrada se verá cómo se puede utilizar TxTorCon para crear servicios ocultos en TOR de forma programática y aunque lo que se verá a continuación también se puede hacer con Stem, se trata de un ejercicio practico muy interesante que servirá para conocer los elementos básicos y la “metodología” que se debe seguir cuando se programa con esta librería.

Antes de continuar, se recomienda al lector tener claros los conceptos básicos sobre la configuración de una instancia de TOR y conocer bastante bien las propiedades admitidas en el fichero “torrc”, aunque crear un servicio oculto no es una tarea compleja ya que solamente es necesario definir la opción de configuración “HiddenService” en el fichero de configuración “torrc” tantas veces como servicios ocultos se desee crear, lo que si que puede ser complicado es mantener el servicio oculto correctamente securizado, pero eso es un tema del que se hablará en un próximo artículo.

En primer lugar, es importante conocer el uso de la clase “txtorcon.TorConfig” ya que en dicha clase es donde definen todos los elementos de configuración de una instancia de TOR y dicho elemento puede ser utilizado para levantar la instancia de forma programática utilizando TxTorCon.

import txtorcon
config = txtorcon.TorConfig()
config.SOCKSPort = 9051
config.ORPort = 4443
…..
config.save()

La clase “txtorcon.TorConfig” maneja un diccionario interno con las propiedades que se pueden definir en un fichero de configuración de TOR, con lo cual el programador debe definir cada propiedad como un atributo de instancia.

Ahora bien, para definir uno o varios servicios ocultos, es necesario crear un listado de instancias de la clase “txtorcon.HiddenService”. Dicho listado se almacenará en la variable “HiddenServices” de la instancia de “txtorcon.TorConfig” creada previamente.
La siguiente función servirá para definir los detalles de configuración básicos para iniciar una instancia de TOR con un servicio oculto.

import txtorcon
import functools
import tempfile
import os
from twisted.internet import reactor 

def createTemporal():
    tempDir = tempfile.mkdtemp(prefix='torhiddenservice')
    reactor.addSystemEventTrigger('before', 'shutdown',
functools.partial(txtorcon.util.delete_file_or_tree, tempDir))
    return tempDir 

def configuration(hiddenserviceDir, serviceInterface,
servicePort=8080, hiddenservicePort=80):
    if hiddenserviceDir is None:
        print "[+] HiddenServiceDir not specified... Generating
a temporal file."
        hiddenserviceDir = createTemporal()
    if os.path.exists(hiddenserviceDir) == False:
        print "[+] The HiddenServiceDir specified does not
exists... Generating a temporal file."
        hiddenserviceDir = createTemporal()
    config = txtorcon.TorConfig()
    config.SOCKSPort = 9051
    config.ORPort = 4443
    config.HiddenServices = [txtorcon.HiddenService(config,
hiddenserviceDir, ["%s %s:%s" %(str(hiddenservicePort),
serviceInterface, str(servicePort))] )]
    config.save()
    return config 

configuration('/home/adastra/Escritorio/django-hiddenservice',
'127.0.0.1')

La función “configuration” se encarga de recibir como argumento todos los elementos necesarios para establecer un servicio oculto en la configuración definida en el objeto “txtorcon.TorConfig” y posteriormente dicho objeto es retornado. Por otro lado, la función “createTemporal” es invocada internamente por la función “configuration” con el fin de devolver un directorio temporal para el servicio oculto en el caso de que el directorio indicado por parámetro sea invalido.

Ahora que la configuración se encuentra preparada, el siguiente paso consiste en utilizarla para iniciar la instancia de TOR en cuestión.

import txtorcon
import functools
import tempfile
import os
from twisted.internet import reactor 

def createTemporal():
    tempDir = tempfile.mkdtemp(prefix='torhiddenservice')
    reactor.addSystemEventTrigger('before', 'shutdown',
functools.partial(txtorcon.util.delete_file_or_tree, tempDir))
    return tempDir 

def configuration(hiddenserviceDir, serviceInterface,
servicePort=8080, hiddenservicePort=80):
    if hiddenserviceDir is None:
        print "[+] HiddenServiceDir not specified... Generating a temporal file."
        hiddenserviceDir = createTemporal()
    if os.path.exists(hiddenserviceDir) == False:
        print "[+] The HiddenServiceDir specified does not exists... Generating a temporal file."
        hiddenserviceDir = createTemporal()
    config = txtorcon.TorConfig()
    config.SOCKSPort = 9051
    config.ORPort = 4443
    config.HiddenServices = [txtorcon.HiddenService(config,hiddenserviceDir, ["%s %s:%s" %(str(hiddenservicePort),serviceInterface, str(servicePort))] )]
    config.save()
    return config 

def updates(prog, tag, summary):
    print "%d%%: %s" % (prog, summary) 

def setup_complete(config, proto):
    print "TOR Instance started!" 

def setup_failed(arg):
    print "SETUP FAILED", arg
    reactor.stop() 

def startTor(config):
    d = txtorcon.launch_tor(config, reactor,progress_updates=updates)
    d.addCallback(functools.partial(setup_complete, config))
    d.addErrback(setup_failed)
    reactor.run()
torrc = configuration('/home/adastra/Escritorio/hidden_service_django','127.0.0.1')
startTor(torrc)

En esta nueva versión del script se ha incorporado la función “startTor”, la cual se encarga de utilizar la configuración retornada por la función “configuration” para iniciar TOR. Como se puede apreciar, dicha función emplea la utilidad “txtorcon.launch_tor” enviando como argumentos, la configuración de TOR, el reactor de Twisted y una función de callback para procesar cada uno de los eventos producidos durante proceso de inicio. Finalmente, se adicionan dos funciones más en el caso de que el proceso de arranque haya ido bien o en el caso de fallo.

Después de ejecutar el script anterior, se podrá ver por consola algo muy similar a lo que se enseña en la siguiente imagen.

txtorcon1

El script puede parecer complejo pero tal como se ha explicado anteriormente, si se conoce el funcionamiento de Twisted y las funcionalidades básicas de TxTorCon, no resulta tan complicado de comprender.
Hasta este punto se asume que en la máquina local se encuentra un servicio levantado y esperando conexiones, más concretamente en el puerto “8080”. Evidentemente, dado el escenario anterior es necesario levantar un servidor web con Tomcat, una aplicación con Django o cualquier otro servicio en dicho puerto, pero dadas las características de Twisted, también es posible crear un servidor web simple directamente desde el script y de esta forma, se contará con una herramienta completamente funcional que puede levantar un servicio oculto sin depender de ningún programa externo (excepto el propio ejecutable de TOR).

import txtorcon
import functools
import tempfile
import os
from twisted.web import static, resource, server
from twisted.internet import reactor
from twisted.internet.endpoints import TCP4ServerEndpoint 

def createTemporal():
    tempDir = tempfile.mkdtemp(prefix='torhiddenservice')
    reactor.addSystemEventTrigger('before', 'shutdown',
functools.partial(txtorcon.util.delete_file_or_tree, tempDir))
    return tempDir 

def configuration(hiddenserviceDir, serviceInterface,
servicePort=8080, hiddenservicePort=80):
    if hiddenserviceDir is None:
        print "[+] HiddenServiceDir not specified... Generating a temporal file."
        hiddenserviceDir = createTemporal()
    if os.path.exists(hiddenserviceDir) == False:
        print "[+] The HiddenServiceDir specified does not exists... Generating a temporal file."
        hiddenserviceDir = createTemporal()
    config = txtorcon.TorConfig()
    config.SOCKSPort = 9051
    config.ORPort = 4443
    config.HiddenServices = [txtorcon.HiddenService(config,hiddenserviceDir, ["%s %s:%s" %(str(hiddenservicePort),serviceInterface, str(servicePort))] )]
    config.save()
    return config 

def updates(prog, tag, summary):
    print "%d%%: %s" % (prog, summary) 

def setup_complete(config, proto):
    print "TOR Instance started!" 

def setup_failed(arg):
    print "SETUP FAILED", arg
    reactor.stop() 

def startTor(config):
    #Starting a simple web site.
    root = static.File('/opt/WebSite')
    site = server.Site(root)
    hs_endpoint = TCP4ServerEndpoint(reactor, 8080,interface='127.0.0.1')
    hs_endpoint.listen(site)
    d = txtorcon.launch_tor(config, reactor,progress_updates=updates)
    d.addCallback(functools.partial(setup_complete, config))
    d.addErrback(setup_failed)
    reactor.run() 

torrc =configuration('/home/adastra/Escritorio/django-hiddenservice','127.0.0.1')
startTor(torrc)

El programa anterior solamente añade los elementos necesarios para declarar un servidor web cuyo directorio raíz es “/opt/WebSite”. Dicho servidor web se levantará en el puerto 8080 en la interfaz de red local, tal como se ha definido en la configuración del servicio oculto. Con todo esto, después de que la instancia de TOR se levante y se creen los ficheros correspondientes al dominio “onion” y a las claves del servicio, cualquier cliente que intente ingresar por dicha la dirección onion del servicio oculto, podrá ver los contenidos del servidor web que se ha iniciado utilizando Twisted. La siguiente imagen enseña algo muy similar a lo que el usuario final verá en su navegador.

txtorcon2

Como se puede apreciar, al acceder a la dirección onion del servicio oculto, se pueden visualizar los contenidos del directorio “/opt/WebSite”, que es el directorio que se ha indicado como raíz del servidor web.

Aunque aquí se ha enseñado como crear un servicio web en la red de TOR, también es posible crear cualquier otro tipo de servicio siguiendo exactamente la misma dinámica que se ha explicado aquí, como por ejemplo por un servidor SSH/SFTP con Paramiko, un servidor FTP o incluso un servidor SMB. Tienes a tu disposición muchas alternativas a la hora de automatizar la creación de servicios ocultos en la web profunda de TOR.

Un Saludo y Happy Hack!

Hacking con Python Parte 25 – Atacando Repetidores de Salida de TOR

julio 22, 2014 1 comentario

Script que utiliza STEM, Python-Nmap y Shodan para atacar los repetidores que se encuentran registrados en los descriptores publicados por las autoridades de directorio.
Se trata de una versión inicial, que modificaré y extenderé en los proximos días.
Publicaré un post para explicar en que consistiran las caracteristicas que quiero implementar y como utilizarlo.

attackTor: https://github.com/Adastra-thw/pyHacks/blob/master/attackTOR.py

Repositorio GIT de la serie:
https://github.com/Adastra-thw/pyHacks.git


Make a Donation Button

Hacking con Python Parte 24 – Consulta de descriptores de TOR con Stem

julio 15, 2014 1 comentario

Conceptos basicos sobre los descriptores de TOR utilizando la API de STEM.

Repositorio GIT de la serie:
https://github.com/Adastra-thw/pyHacks.git


Make a Donation Button

Hacking con Python Parte 23 – Controlando instancias de TOR con Stem

julio 8, 2014 2 comentarios

Utilizando la API de Stem para acceder a repetidores locales de TOR.

Repositorio GIT para la serie:
https://github.com/Adastra-thw/pyHacks.git


Make a Donation Button

TORTAZO para auditar nodos de salida de TOR

marzo 5, 2014 6 comentarios

Hace algunos meses he comenzado a jugar con Stem para TOR (https://stem.torproject.org/ ) y claro, ya que se trata de una librería muy completa y que permite extraer casi cualquier tipo de información sobre los repetidores conectados en la red de TOR, una cosa llevo a la otra y al final he terminado creando TORTAZO.

Se trata de una herramienta que aun se encuentra en estado de desarrollo y que de momento tiene las siguientes características:

  • Permite extraer información de los Server Descriptors del último consenso emitido por las autoridades de directorio y filtrar por sistema operativo y número de repetidores máximo a recuperar.
  • Realiza un escaneo inicial contra los nodos encontrados utilizando Nmap y genera un fichero de texto con los puertos abiertos para cada una de las máquinas encontradas.
  • En el caso de que tengamos el fingerprint del nodo de salida que queremos auditar, podemos realizar la extracción de información y posterior análisis utilizando como filtro ese fingerprint
  • Después de realizar el escaneo con Nmap, opcionalmente Tortazo puede buscar en Shodan cualquier información adicional sobre el nodo de salida.
  • Opcionalmente, permite realizar ataques por diccionario contra servidores SSH y FTP. En tal caso, admite como argumento un diccionario conformado por pares de usuarios y claves. Si no se especifica un fichero de diccionario, Tortazo utilizará algunos de los ficheros de usuarios y passwords existentes en el proyecto FuzzDB (para la primera versión de Tortazo, utiliza la versión 1.09 de FuzzDB que es la última disponible). Este proceso, como todos los ataques de “bruteforcing”, es muy ruidoso y puede llevar mucho tiempo en ejecutarse.
  • En el caso de que se consiga acceso a un servidor SSH, se actualiza el fichero tortazo_botnet.bot el cual contiene en cada linea, el host, usuario y contraseña. Esta información luego es utilizada para ejecutar comandos de forma paralela sobre todos los servidores SSH definidos en dicho fichero o solamente sobre un conjunto determinado.

Esto es un resumen de las características que he incluido en la primera versión de está herramienta, sin embargo, mi imaginación tiende a volar y constantemente se me van ocurriendo cosas que me gustaría hacer. Para las nuevas versiones que comenzaré a desarrollar desde mañana (en mis ratos libres, porque desafortunada o afortunadamente, según se mire, tengo que currar) incluiré las siguientes funcionalidades:

  • Integración de herramientas como Nessus, OpenVAS y Metasploit
  • Generar informes un poco más “profesionales” que simplemente ficheros de texto
  • Incluir las nuevas características de la API de Shodan.
  • Recolectar información sobre dispositivos con SNMP y detectar aquellos que tienen nombres de comunidades por defecto.
  • Implementar un sistema de plugins que le permita a otras personas integrar sus rutinas de código en Tortazo.
  • Implementar funciones para GeoLocalización de los servidores encontrados (usando varias bases de datos de GEOLocalización).
  • Analizar más protocolos… (HTTP/HTTPS, SMTP, POP, NNTP, NTP, SMB). El cielo es el limite 😛

Creo que la versión 1.1 será la que realmente le empezará a dar forma a Tortazo, el tiempo lo dirá, pero de momento la primera versión servirá como base para desarrollar las demás características que se me vayan ocurriendo.

Si te parece interesante lo que te estoy contando y quieres saber un poco más, he incluido más detalles en el fichero README del proyecto, el cual se encuentra en el repositorio GitHub: https://github.com/Adastra-thw/Tortazo
Si quieres colaborar en el desarrollo, ya sea con código o con ideas que puedan implementarse, estoy abierto a sugerencias 🙂

 Un Saludo y Happy Hack!

A %d blogueros les gusta esto: