Machine - Forge - Active - Medium
PORT STATE SERVICE REASON
22/tcp open ssh syn-ack ttl 63
80/tcp open http syn-ack ttl 63
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 8.2p1 Ubuntu 4ubuntu0.3 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 3072 4f:78:65:66:29:e4:87:6b:3c:cc:b4:3a:d2:57:20:ac (RSA)
| 256 79:df:3a:f1:fe:87:4a:57:b0:fd:4e:d0:54:c6:28:d9 (ECDSA)
|_ 256 b0:58:11:40:6d:8c:bd:c5:72:aa:83:08:c5:51:fb:33 (ED25519)
80/tcp open http Apache httpd 2.4.41
|_http-title: Did not follow redirect to http://forge.htb
|_http-server-header: Apache/2.4.41 (Ubuntu)
Service Info: Host: 10.10.11.111; OS: Linux; CPE: cpe:/o:linux:linux_kernel
- let’s add a forge.htb to the host
exploration
- we can upload images… (vector attack)
- we can request from url
FUZZ
- there is an admin domain admin.forge.htb
Only localhost is allowed!
- using the download images from http, we could connect to the admin and saw a credential for an ftp
user:heightofsecurity123
<li>An internal ftp server has been setup with credentials as user:heightofsecurity123!</li>
<li>The /upload endpoint now supports ftp, ftps, http and https protocols for uploading from url.</li>
<li>The /upload endpoint has been configured for easy scripting of uploads, and for uploading an image, one can simply pass a url with ?u=<url>.</li>
- ssh only allows to login with key… which makes me think if we can get some id_rsa or upload an authorized_…
<div id="content">
<h2 onclick="show_upload_local_file()">
Upload local file
</h2>
<h2 onclick="show_upload_remote_file()">
Upload from url
</h2>
<div id="form-div">
</div>
</div>
function show_upload_local_file(argument) {
var form_div = document.getElementById('form-div');
form_div.innerHTML = `
<form action="/upload" method="POST" enctype="multipart/form-data">
<input type="file" name="file" class="file">
<input name="local" type="hidden" value='1'>
<br>
<br>
<button id="submit-local" type="submit" class="submit">Submit</button>
</form>
`;
}
function show_upload_remote_file(argument) {
var form_div = document.getElementById('form-div');
form_div.innerHTML = `
<br><br>
<form action="/upload" method="POST" enctype="application/x-www-form-urlencoded" >
<input type="textbox" name="url" class="textbox">
<input name="remote" type="hidden" value='1'>
<br>
<br>
<button id="submit-remote" type="submit" class="submit">Submit</button>
</form>
`;
}
with a bit of twerking the urlencode, we get to see the user flag :)
also we can read the .ssh/id_rsa and with that we can log into the user with ssh :D
user to …
sudo ⇒ (ALL : ALL) NOPASSWD: /usr/bin/python3 /opt/remote-manage.py
#!/usr/bin/env python3
import socket
import random
import subprocess
import pdb
port = random.randint(1025, 65535)
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
sock.bind(('127.0.0.1', port))
sock.listen(1)
print(f'Listening on localhost:{port}')
(clientsock, addr) = sock.accept()
clientsock.send(b'Enter the secret passsword: ')
if clientsock.recv(1024).strip().decode() != 'secretadminpassword':
clientsock.send(b'Wrong password!\n')
else:
clientsock.send(b'Welcome admin!\n')
while True:
clientsock.send(b'\nWhat do you wanna do: \n')
clientsock.send(b'[1] View processes\n')
clientsock.send(b'[2] View free memory\n')
clientsock.send(b'[3] View listening sockets\n')
clientsock.send(b'[4] Quit\n')
option = int(clientsock.recv(1024).strip())
if option == 1:
clientsock.send(subprocess.getoutput('ps aux').encode())
elif option == 2:
clientsock.send(subprocess.getoutput('df').encode())
elif option == 3:
clientsock.send(subprocess.getoutput('ss -lnt').encode())
elif option == 4:
clientsock.send(b'Bye\n')
break
except Exception as e:
print(e)
pdb.post_mortem(e.__traceback__)
finally:
quit()
since there is a pdb at the end… when we do Ctrl-c we bring an exception and… boom we have a python shell, we can import os.system and execute commands as root.