BRC 4
BRC 4
Version 1.7
Table of Contents
Introduction To Brute Ratel C4 [BRc4]..................................................................................7
System Requirements........................................................................................................ 7
Ratel Server.....................................................................................................................................7
Commander...................................................................................................................................8
Badger.............................................................................................................................................9
Brute Ratel Callback.....................................................................................................................10
User Interface – Commander...............................................................................................11
Scratchpad........................................................................................................................ 12
Command Queue............................................................................................................. 12
Chatbox............................................................................................................................ 12
Commander Settings....................................................................................................... 12
Operators......................................................................................................................... 13
Listeners........................................................................................................................... 14
HTTP Listener...............................................................................................................................14
DNS Over HTTPS Listener..........................................................................................................18
Listener Interaction......................................................................................................................22
Listener Actions.......................................................................................................................22
Staging.....................................................................................................................................23
Stageless Badgers..................................................................................................................24
Riot Control.............................................................................................................................24
Pivot Graphs............................................................................................................................25
KillSwitch..................................................................................................................................25
WebHooks...............................................................................................................................26
Profiles............................................................................................................................. 28
Payload Profiles...........................................................................................................................28
Command Profiles.......................................................................................................................32
Autorun Profiles...........................................................................................................................35
Clickscript Profiles.......................................................................................................................35
Hosting Files................................................................................................................................36
Root Page Changer.......................................................................................................... 37
PsExec Configuration....................................................................................................... 37
Socks Proxy (4a/5)........................................................................................................... 38
Reverse Port Forwarding................................................................................................. 38
TCP Listeners................................................................................................................... 39
Credentials....................................................................................................................... 39
Logging and Downloads.................................................................................................. 40
Operator Activity.............................................................................................................. 41
MITRE Graphs.................................................................................................................. 42
Shortcut Keys................................................................................................................... 42
Badger Core.........................................................................................................................44
Indirect System Calls....................................................................................................... 45
Hiding Shellcode Sections in Memory.............................................................................47
Sleeping Masking Techniques......................................................................................... 47
Masquerade Thread Stack Frame..............................................................................................47
www.bruteratel.com 2
Command: set/get obfsleep..................................................................................................47
Command: set/get start_address.........................................................................................50
Thread Stack and Heap Encryption, Secure Heap-Free..........................................................51
Advanced Module Stomping with PEB Hooking......................................................................51
Full PEB Linking and Entrypoint Patching............................................................................52
Control Flow Guard................................................................................................................52
Module Stomping Evasion.....................................................................................................53
Unhooking EDR Userland Hooks and Dlls.......................................................................54
Proxying LoadLibrary for ETW Evasion...........................................................................55
Unhooking DLL Load Notifications..................................................................................57
Hardware Breakpoint for AMSI/ETW Evasion.................................................................57
Reusing Virtual Memory For ETW Evasion......................................................................58
Reusing Loaded Libraries from PEB................................................................................58
In-Memory RDLL Execution............................................................................................ 58
In-Memory PE Execution................................................................................................. 59
Command: memexec..................................................................................................................59
In-Memory BOF Execution.............................................................................................. 60
Command: coffexec....................................................................................................................60
Command: set_coffargs/clear coffargs....................................................................................63
Module stomping for BOF/Memexec..............................................................................64
Command: set/get/clear module_stomp.................................................................................64
In-Memory Dotnet Execution.......................................................................................... 64
Command: sharpinline/sharpreflect..........................................................................................64
Network Malleability and External C2 Specification........................................................65
Badger Interaction...............................................................................................................67
Load................................................................................................................................. 68
Load Adjacent Tab........................................................................................................... 68
Load New Window.......................................................................................................... 68
Clear Cmd-Q................................................................................................................... 68
Arsenal............................................................................................................................. 68
LDAP Sentinel..............................................................................................................................69
Switch Profile...............................................................................................................................69
Process Manager.........................................................................................................................70
File Explorer..................................................................................................................................71
Crypt Vortex..................................................................................................................................72
Load ClickScript............................................................................................................... 74
Remove............................................................................................................................ 74
Export To CSV.................................................................................................................. 74
Mark Dead........................................................................................................................ 75
Color................................................................................................................................ 75
Exit Thread....................................................................................................................... 75
Exit Process...................................................................................................................... 75
Badger Commands..............................................................................................................75
Process Injection.............................................................................................................. 76
Command: set/clear dllblock......................................................................................................76
Command: set/get malloc...........................................................................................................77
www.bruteratel.com 3
Command: set/get threadex.......................................................................................................78
Command: set/get/clear parent.................................................................................................78
Command: set/get/clear child....................................................................................................79
Command: set/get/clear spoof_args........................................................................................79
Command: set/clear cfg..............................................................................................................80
Command: suspended_run........................................................................................................81
Command: loadr...........................................................................................................................81
Command: memhook.................................................................................................................82
Command: phantom_thread.....................................................................................................83
Command: threads......................................................................................................................85
Command: psimport/clear psimport.........................................................................................85
Command: psreflect....................................................................................................................85
Command: shinject_ex...............................................................................................................86
Windows Services........................................................................................................... 86
Command: sccreate....................................................................................................................86
Command: scdelete....................................................................................................................87
Command: scdivert.....................................................................................................................87
Command: scquery.....................................................................................................................87
Command: scstart.......................................................................................................................88
Command: scstop.......................................................................................................................88
Network Enumeration & Interaction...............................................................................88
Command: arp.............................................................................................................................88
Command: curl............................................................................................................................89
Command: dns_interval.............................................................................................................89
Command: dnscache..................................................................................................................90
Command: download.................................................................................................................90
Command: icmp_ping.................................................................................................................91
Command: ipstats........................................................................................................................91
Command: lookup.......................................................................................................................92
Command: netshares..................................................................................................................92
Command: netstat.......................................................................................................................93
Command: pivot_smb................................................................................................................93
Command: pivot_tcp/get tcppivot............................................................................................94
Command: portscan....................................................................................................................95
Command: ps_ex........................................................................................................................96
Command: psexec.......................................................................................................................97
Command: query_session..........................................................................................................97
Command: routes........................................................................................................................98
Command: rportfwd...................................................................................................................98
Command: sharescan.................................................................................................................99
Command: sleep.........................................................................................................................99
Command: upload.......................................................................................................................99
Command: socks/socks_stop....................................................................................................99
Command: switch_profile.........................................................................................................101
Local Enumeration......................................................................................................... 101
Command: acl.............................................................................................................................101
www.bruteratel.com 4
Command: applist......................................................................................................................102
Command: cd.............................................................................................................................102
Command: cp.............................................................................................................................102
Command: crisis_monitor........................................................................................................103
Command: drivers.....................................................................................................................104
Command: dumpclip.................................................................................................................104
Command: exit_process...........................................................................................................105
Command: exit_thread.............................................................................................................105
Command: fileinfo.....................................................................................................................105
Command: idletime...................................................................................................................105
Command: keylogger................................................................................................................105
Command: kill............................................................................................................................106
Command: list_modules..........................................................................................................106
Command: local_sessions.......................................................................................................106
Command: lockws.....................................................................................................................107
Command: ls..............................................................................................................................107
Command: lsdr..........................................................................................................................108
Command: mkdir/rmdir............................................................................................................108
Command: mv...........................................................................................................................108
Command: preview...................................................................................................................109
Command: ps.............................................................................................................................109
Command: psgrep.....................................................................................................................109
Command: pwd..........................................................................................................................110
Command: record_screen........................................................................................................110
Command: reg............................................................................................................................110
Command: rm..............................................................................................................................111
Command: run.............................................................................................................................111
Command: schtquery.................................................................................................................112
Command: screenshot...............................................................................................................113
Command: shellspawn..............................................................................................................114
Command: stop_task.................................................................................................................114
Command: sysinfo......................................................................................................................114
Command: timeloop..................................................................................................................115
Command: uptime.....................................................................................................................116
Command: userinfo....................................................................................................................116
Command: windowlist...............................................................................................................117
Active Directory Enumeration........................................................................................ 118
Command: dcenum....................................................................................................................118
Command: dcsync......................................................................................................................118
Command: net............................................................................................................................119
Command: passpol....................................................................................................................120
Command: sentinel....................................................................................................................121
Command: set/get sentinel_sleep...........................................................................................122
Credential Harvesting.................................................................................................... 122
Command: make_token/revtoken...........................................................................................122
Command: addpriv....................................................................................................................123
www.bruteratel.com 5
Command: get_system.............................................................................................................123
Command: grab_token.............................................................................................................124
Command: get token_vault......................................................................................................125
Command: vault_remove.........................................................................................................125
Command: clear vault................................................................................................................126
Command: impersonate...........................................................................................................126
Command: kerberoast...............................................................................................................126
Command: memdump..............................................................................................................127
Command: mimikatz.................................................................................................................128
Command: phish_creds............................................................................................................129
Command: pth............................................................................................................................129
Command: runas.......................................................................................................................130
Command: samdump...............................................................................................................130
Command: shadowcloak...........................................................................................................131
Command: system_exec...........................................................................................................131
Windows Management Instrumentation.......................................................................131
Command: set/get/clear wmiconfig/wmiexec/wmiquery.....................................................131
Command Configurations.............................................................................................. 132
Command: set............................................................................................................................132
Sub-command: set killdate..................................................................................................133
Sub-command: set env........................................................................................................133
Command: get............................................................................................................................133
Sub-command: get tasks.....................................................................................................133
Sub-command: get killdate.................................................................................................133
Sub-command: get env........................................................................................................133
Commander Commands................................................................................................ 134
Command: cls............................................................................................................................134
Command: clearq.......................................................................................................................134
Command: help..........................................................................................................................134
Command: note.........................................................................................................................134
Command: title..........................................................................................................................134
www.bruteratel.com 6
Introduction To Brute Ratel C4 [BRc4]
Brute Ratel is a highly advanced Red Team & Adversary Simulation Software. It
can emulate different stages of an attacker kill chain and provide a systematic
timeline to help the Security Operations team validate the attacks to improve
their internal defense mechanism. Brute Ratel comes prebuilt with several
operational security features that can severely reduce the overhead of Red Teams
allowing them to focus more on the analytical part of an engagement instead of
depending on open-source tools or manual calibration of the C2 framework for
post-exploitation activities. Brute Ratel is a post-exploitation C2 in the end
and however does not provide exploit generation features like Metasploit or
vulnerability scanning features like Nessus, Acunetix, or BurpSuite. Using Brute
Ratel requires some understanding of windows internals in order to leverage the
product to its full potential. This manual describes the intricate parts of the
BRc4 Framework.
1. Ratel Server
2. Commander
3. Badger
Ratel server is an extremely fast API server. An operator can use Commander –
the graphical user interface or the API documentation provided with this package
to communicate with the server. Ratel server can operate over AMD or ARM x64
Linux operating system. Commander is the graphical user interface that
communicates with the Ratel server. It is available in AMD x64 flavor for
Windows/Linux and Arm x64 Apple Silicon for Mac. An operator can use Commander
to interact with the ratel server or payload. Payloads in Brute Ratel are called
Badgers. Badgers are currently limited to Windows operating systems ranging from
Windows Vista to Windows 11 inclusive of the server versions.
System Requirements
Ratel Server
The Ratel server is an API-driven server. Operators can use the API
documentation provided alongside the BRc4 package to automate some of the tasks
that are normally performed using Commander. Ratel server primarily operates
over WebSocket which takes API requests from Commander/API and either consume
the request or forward the command to the badger. All requests and responses,
sent and received by the Ratel server are in JSON. Ratel server also accepts a
few command-line arguments. The operator can start the server by providing the
required command-line arguments, or by providing a JSON configuration file
(henceforth called a C4 Profile) and automate several tasks on the server. When
a server is started for the first time, the operator has to supply the admin
username, password, SSL certificate, SSL key file, and the server handler IP
address and port which the Commander will connect to.
To run the Ratel server, install the below dependencies on a Linux operating
system:
www.bruteratel.com 7
sudo apt-get install nasm mingw-w64
{
"c2_handler": "0.0.0.0:8443",
"ssl_cert": "cert.pem",
"ssl_key": "key.pem"
}
Once a server is started, it autosaves the whole profile every 10 seconds into a
local JSON file named autosave.profile. For some reason, if a server restart is
required, the following command can restore the entire server operation using
the autosave.profile.
Commander
To make the best use of Commander, it is recommended to use Ubuntu 20.04 with
Gnome or KDE desktop environments. Commander is built in QT++ and comes pre-
packaged with all its requirements. However, it works much better visually when
used in a QT-dependent environment like Gnome or KDE. The package contains three
operating system flavors and their respective shell scripts. To run Commander,
execute:
Once Commander is executed, the operator has to enter the ratel server
information. The C2 host format is ‘ip:port’ and the rest should be self-
explanatory.
www.bruteratel.com 8
Badger
Badger is the implant that is generated by the Ratel Server. Badger executes on
all systems from Windows Vista till the latest release of Windows 11 (incl. All
server versions). This release of Brute Ratel generates implants in the
following types:
1. Stage Zero
2. Stageless
Stage zero is available in two flavors: x64 and x86 for windows. Both versions
use indirect syscalls, but only the x64 version supports unhooking EDRs
alongside various stealth capabilities. Stage zero payloads can only be
generated as a shellcode which can be exported into raw binary format (bin) to
disk.
1. x64 Default
1. Shellcode – RtlExitUserThread
2. Shellcode – WaitForSingleObject
3. DLL
4. Service Executable
2. x64 Stealth
1. Shellcode – RtlExitUserThread
2. Shellcode – WaitForSingleObject
3. Service Executable
3. x86 Default
1. Shellcode – RtlExitUserThread
2. Shellcode – WaitForSingleObject
3. DLL
4. Service Executable
More information regarding each of the badger types is discussed later in the
section here and here.
www.bruteratel.com 9
Brute Ratel Callback
Brute Ratel only calls back to bruteratel.com on port 65000 when the operator
requests the activation. Apart from the activation, Brute Ratel does not perform
any remote connection. The Brute Ratel package can only be updated by navigating
the downloads page of bruteratel.com. If you have lost your license key, you can
request a duplicate key by contacting [email protected].
www.bruteratel.com 10
User Interface – Commander
The below user interface is presented to the operator on the first login.
1. Operators can use the Add War Room button to add additional tabs for other
Ratel servers or exit the user interface by selecting the cross icon on an
open tab.
2. These are various menus for the operator to configure the Ratel server or
badger.
4. This area shows a quick status of the Commander’s connection with the
Ratel server. If this is red, it means the server connection is dead. If
the smiley face is happy, it means Commander is idle, and if badgers are
checking in, then the smiley changes to a more serious face (O_O), which
means packets are being transmitted between the Commander and the Server.
5. This table displays active listeners, active and dead badgers, harvested
credentials stored on the Ratel server, and downloaded files from various
badgers on this Ratel server.
6. This area shows the event log which is synchronized with the logs
displayed on the terminal of the Ratel server. Event logs display a
variety of information about operations performed while interacting with
the Ratel server or the badger
www.bruteratel.com 11
operators. These chat logs are ephemeral, meaning they are not saved
anywhere on the server’s memory or in logs.
8. The last web activity area displays recent events on the Ratel server’s
handler port and the listener ports. This is useful to monitor if anyone
is interacting with the open ports on the Ratel server.
Scratchpad
Scratchpad is a simple text editor that can take quick notes, view logs,
downloaded text files, C4 profiles, and any other type of text file. It stores
everything temporarily in memory. The first button View Server Configuration can
view the server’s current configuration or profile. It prints everything in JSON
and can be copied to a local file to be used later as a profile. The third
button View PsExec Configuration displays the current configuration of PsExec.
This configuration can be changed from C4 Profiler->PsExec Config. An operator
can hover over each of the buttons to identify their use case.
Command Queue
Badgers are asynchronous in nature. Once a badger completes its sleep cycle, it
will connect to the server to request all the tasks in the queue, download the
tasks, run the requested tasks, and return a response the next time it checks
in. When a badger is sleeping, the commands are queued on the server. The
Command Queue lists all the commands that are not yet retrieved by the badger.
Once the commands are received by the badger, it is removed from the server.
Chatbox
The chatbox can communicate with other operators who have joined the
communication channel. The operators won’t get notifications if they are not
connected to the channel. All chats are ephemeral in nature and all operators
who want to chat have to be connected to the chat channel to send and receive
data.
Commander Settings
Some settings of Commander can be changed from the Commander dropdown menu.
www.bruteratel.com 12
The Settings selection can change the theme, font size, or font family of
Commander. The default font is Monospace and the font size is set to 10. An
operator can also write QSS stylesheets to change the themes of Commander. More
information on QSS stylesheets can be found here. The default theme of Commander
is dark, but two separate stylesheets, light and shady (material dark) are
provided in the lib64-linux directory within the BRc4 package. An operator can
use these samples to generate custom themes or provide the existing theme file
path in the command-line option to start the Commander with the specified theme
file.
Operators
Users in Brute Ratel are called Operators. Operators can be configured either by
adding their username/password directly into a C4 profile or by adding them
manually through Commander. Only one Admin can be created in Brute Ratel. The
rest of the operators will always be unprivileged operators. Only an admin
operator can add, delete, and change an operator’s password. The rest of the
operators can only change their own passwords. To add a new operator, select
Operator->Add Operator and enter the new operator’s username and password. To
remove an existing operator, select Operator->Delete Operator and select the
www.bruteratel.com 13
operator to remove from the dropdown list. To reset an operator’s password,
select Operator->Change Password and select the operator from the dropdown list.
Now enter the new password and the operator’s password will reset.
{
"admin_list": {
"admin": "pass123"
},
"user_list": {
"operator1": "password123",
"operator2": "password456"
}
}
Listeners
HTTP Listener
To create a new HTTP/HTTPS listener, select C4 Profiler->Add HTTP Listener.
Listener Name: This is a unique listener name. The listener name is auto-
generated and can be modified only during listener creation.
Listener bind host: This is the IP address on which the ratel server will bind
to. It can be an internal IP or external depending on the cloud environment.
Rotational hosts: The rotational hosts are servers where the payload checks in
from time to time, eg.: xyz.azureedge.net, xyz.cloudfront.net, etc. Any number
of rotational hosts can be added here separated by a comma. These hosts get
embedded in the badger in an encrypted context. These can also be a combination
of IP addresses, fronted domains, redirectors, or general domains. When a badger
checks in, it will select a random host from the list of rotational hosts. This
happens every time it needs to check in. Rotational hosts are not fallback
hosts. Fallback profiles work differently. For example, if three rotational
hosts are added, and one of them fails to connect, the badger will still use all
three hosts to select a random one out of them, the next time it tries to
connect. The failed host is not discarded. If failed hosts are to be discarded,
the operator has to configure the fallback profile.
Port: This is the port on which the listener binds to. An operator can create a
listener binding on a non-standard port and use Nginx proxy to route the traffic
to the listener. An operator can use Payload Profiles to change the port of the
badger and generate badgers from these profiles. For example, two listeners can
be started on 127.0.0.1:8443 and 127.0.0.1:9443. Now, we can use nginx to listen
on port 443 and forward all requests received on this port to either port 8443
or 9443 on localhost after filtering the requests by URI or User-agent. We can
configure the badger’s port separately from the listener by using C4 Profiler-
>Profiles->Payload Profiles, and generating a payload from here. This way the
badger can connect to wherever an operator wants, and the listener is hidden
behind the Nginx proxy to avoid its internet exposure.
User-agent: This is the user-agent sent by the badger in its HTTP/HTTPS request.
www.bruteratel.com 14
URI: These URIs are sent in the HTTP request by the badger. These URIs are a
part of the auth system and badgers do not connect to any URI apart from these.
If the URI on the listener is taken down, then badger requests on these URIs
will also be dropped.
OS: This is the operating system for the payload. Currently, only Windows is
supported.
SSL: The SSL configuration for HTTPS payloads can be enabled (true) or disabled
(false). All data within these requests are encrypted using a custom encryption
algorithm irrespective of whether SSL is enabled or disabled.
HTTP proxy: This is the internal proxy to which the badger sends the request.
Badgers are proxy-aware by default. But if an operator wants it to connect
elsewhere, it can be done by adding the proxy information here.
Sleep mask: The sleep mask defines the obfuscation strategy during badger sleep
intervals. An operator can select between three techniques: Asynchronous
Procedure Call (APC), Thread Pooling Technique one, or Thread Pooling technique
two. More info on this can be found in section here.
Stomp Module: The module which gets stomped by the badger, can be defined here.
Module stomping is a technique where the shellcode of the badger loads the
defined module (DLL) into memory and overwrites its .text section with the
contents of the badger’s shellcode. Now all threads originating from the
shellcode of the badger will be backed by the stomped DLL making it harder for
EDRs to differentiate between a bad call stack and the legitimate ones. Make
note that the .text section’s size of the stomped DLL should be greater than or
equal to, the size of the badger’s shellcode as badger will reside in there.
Unlike other C2 frameworks, where stomping on a module can lead to detections
via PEB or by comparing it with the legitimate module on disk, badger performs
module stomping in an entirely different way where PEB is patched to make it
look legitimate and the original buffer of the DLL is also restored during
sleep. More information regarding sleep masking is discussed later in the
Badger’s chapter.
Default sleep: This defines the sleep and jitter interval of the badger. The
sleep number is defined in seconds and the jitter interval is the percentage of
the sleep. Once sleep and jitter are defined, a random value between the sleep
value and the jitter percentage is selected and added to the sleep value to
perform the actual sleep.
www.bruteratel.com 15
Each profile can contain an encrypted fallback profile metadata and the fallback
profile can contain another profile and so on. The fallback profile is just
another HTTP or DOH profile. This option can be configured either from Commander
or via a C2 profile such as:
{
"listeners": {
"primary-c2": {
// ... your primary profile data
"fallback": "fallback-c2",
"fallback_counter": 10
},
"fallback-c2": {
// .. fallback profile 1 data
"fallback": "fallback-c2-2",
"fallback_counter": 5
}
"fallback-c2-2": {
// .. fallback profile 2 data
}
}
}
Fallback counter: This option configures the number of attempts that are made to
connect to the primary profile before falling back to the backup ones. A
detailed explanation of the fallback profile can be found here.
Auth (Common/OTA): The Ratel server provides two types of authentication: Common
Authentication for all badgers and One Time Authentication (OTA). If Common Auth
is selected, all badgers will have the same authentication key. Any badger that
checks in for the first time, will provide an encrypted key to the listener,
without which the listener will send a 404 Not Found to the badger. However, for
phishing activities, it's a better idea to generate OTA keys. This way when a
badger connects for the first time, the key will be authenticated, the badger
will receive a token and then the key will be purged from the server. Thus, if a
security team gets hold of the same payload, it will never be able to
authenticate to the server and the server will always reject the OTA key since
it does not exist anymore. BRc4 listener provides the option to either manually
www.bruteratel.com 16
type in multiple comma-separated keys, or to select the checkbox Create random
set of authentication keys to request the ratel server to auto-generate them. If
you decide to let the listener create random keys, the keys can be viewed by
right clicking the listener and selecting Listener Actions->View Authentication.
The authentication key can be changed using Listener Actions->Change
Authentication.
Malleable Profiles - Post Request: An operator can prepend and append a set of
strings to the data sent by the badger to simulate traffic from AWS, Azure, etc.
Configuring this option specifies how the badger will embed its encrypted and
encoded data in the badger's request.
Malleable Profiles - Post Response: Similar to the above option, an operator can
configure how the server responds to the badger. Configuring this option
specifies what strings the server can append and prepend to the response sent to
the badger.
Malleable Profiles - Empty Response: During long sleep intervals, there might be
a possibility that the server might not have any commands in queue. In such
cases, the server can just send this response to let the badger know there are
no commands in the queue. The default response from the server is HTTP 200 OK.
The below table describes the key-value pair to generate a listener JSON profile
www.bruteratel.com 17
autogenerate keys. Reserved for future use
die_offline boolean Should be 'true' or 'false. ‘true’ kills the payload if Yes
internet connectivity is not available during initial
connection.
os_type string Should be 'windows'. Reserved for future use. No
sleep number Sleep time for the badger Yes
jitter number Jitter percentage for the sleep time of the badger Yes
stomp string Module used by badger for Advanced module stomping Yes
fallback string Fallback profile name. This should exist before adding it Yes
to the listener
fallback_counter number Number of attempts before switching to the fallback Yes
profile
proxy string Optional proxy server which can be added to override Yes
the default proxy-aware settings
proxy_user string Proxy server’s username Yes
proxy_pass string Proxy server’s password Yes
obfsleep string Specifies the obfuscation strategy for badger during No
sleep. Options are: APC, Pooling-0 or Pooling-1
append string Data to be appended to the badger’s post request Yes
append_response string Data to be appended to the server’s response Yes
prepend string Data to be prepended to the badger’s post request Yes
prepend_response string Data to be prepended to the server’s response Yes
empty_response string Data sent by the server to indicate there are no Yes
commands in queue
request_headers object Array of headers to be added by badger in it’s request Yes
response_headers object Array of headers to be added by the server in it’s Yes
response
www.bruteratel.com 18
which will then request TXT records instead of A records. An important note here
is to remember that DNS can only transmit a total of 64 bytes per request per
subdomain, unlike post requests where at least 8192 bytes can be sent per chunk.
This means DOH badgers will be several times slower than HTTP badgers as they
will have to send requests and receive responses in multiple chunks. The
malleable DOH listener of Badger also provides an option to return a legitimate
TXT record if there is a normal DNS request by anyone else apart from the
badger. Such requests are logged under “Suspicious DNS records” in the event
logs. However, make note that sometimes, even DNS resolvers such as dns.google
or cloudflare would send the same requests multiple times due to its UDP nature.
Such requests are also logged as suspicious as the ratel server itself doesn’t
know whether it is sent by a general user or by the server.
DNS hosts: Domains that will be stored in the DOH badger that are queried for
various DNS requests by the DOH resolver.
Check-In A Record: When the badger connects to the DOH listener, if the listener
has commands to send, it will request the badger to check-in to receive the TXT
record via this IP Address.
Idle-A Record: When the badger has large data to send to the DOH listener, the
badger will send this A record request.
Spoofed-TXT Record: When the listener has completed sending the data, it will
send this TXT record as a confirmation response.
Rotational hosts: The rotational hosts are DOH resolvers where the badger checks
in from the target’s network. Any number of rotational hosts can be added here.
These hosts get embedded in the badger and are used to randomly switch domains
when they check-in. These rotational hosts need to be valid HTTP DNS Resolvers
such as dns.google, doh.opendns.com, cloudflare-dns.com, etc.
www.bruteratel.com 19
Port: This is the port on which the listener binds to. The DOH listener starts
on port 53 by default, and the requests by the badgers are sent to port 443 of
the DNS resolver (eg.: dns.google) inside a POST or GET request over HTTPS. The
badger configuration can be changed from C4Profiler->Profiles->Payload Profiles
if the request is to be sent elsewhere.
URI: For DOH, the URI has to be dns-query as per the DOH RFC.
DNS Request Interval: Multiple DNS chunks are combined together to send one full
set of data. The interval between each DNS chunk (64 bytes) can be defined here
in milliseconds.
www.bruteratel.com 20
When working around DOH listeners, it’s a good idea to temporarily enable debug
logs for the DOH server. An operator can enable/disable debug logs by selecting
Server->Enable/Disable DOH Debug Logs in Commander.
NOTE: Enabling Debug logs for DOH will slow down the badger’s response and
request time. It should only be used for testing the DOH listener and badger,
and not during a live assessment.
Both HTTP and DOH listener dialogs provide an option to load the listener’s JSON
profile. This configuration is the same configuration that an operator can
extract and save from the scratchpad of any previous listeners.
The below table describes the key-value pair to generate a listener JSON profile
www.bruteratel.com 21
ssl boolean Set to true to enable SSL, else false No
useragent string UserAgent for the payload. Acts as a part of No
authentication for the badger
c2_uri array This has to be “dns-query” No
auth_count number Authentication key count No
auth_type boolean False implies regular keys and true implies OTA No
c2_authkeys array Comma-separated keys in an array No
is_random boolean Should be 'false'. It is created by the server to No
autogenerate keys. Reserved for future use
die_offline boolean Should be 'true' or 'false. ‘true’ kills the payload if Yes
internet connectivity is not available during initial
connection.
os_type string Should be 'windows'. Reserved for future use. No
sleep number Sleep time for the badger Yes
jitter number Jitter percentage for the sleep time of the badger Yes
stomp string Module used by badger for Advanced module stomping Yes
fallback string Fallback profile name. This should exist before adding it Yes
to the listener
fallback_counter number Number of attempts before switching to the fallback Yes
profile
proxy string This is an optional proxy server which can be added to Yes
override the default proxy-aware settings
proxy_user string Proxy server’s username Yes
proxy_pass string Proxy server’s password Yes
obfsleep string Specifies the obfuscation strategy for badger during No
sleep. Options are: APC, Pooling-0 or Pooling-1
Listener Interaction
Right-clicking a listener provides various options to interact with the
listener.
Listener Actions
This option can edit or stop a listener, view the authentication keys, change
the authentication key or host a file on the listener.
www.bruteratel.com 22
Staging
This can also be enabled from the listener profile by adding the key-value for
stager as follows:
{
"listeners": {
"primary-c2": {
...
"stager": {
"profile": "DOH",
"stage_count": 20
}
}
}
}
A staging listener can select any other profile for staging too. The above
example shows an HTTP listener providing staged badger for a profile named DOH.
The staging would be automatically shutdown once 20 stages have been requested.
Staged badgers are only available in stealth mode for x64 badgers. The size of
the staged badgers is between 9.5 to 20Kb depending on the size of the malleable
profile.
www.bruteratel.com 23
Stageless Badgers
Stageless badgers account from 234-300Kb depending on the size of the malleable
profile. Stageless badgers are available in a variety of flavors. The default-
implant is suitable when dealing with Kernel-Only EDRs, whereas the stealth-
implant is suitable when dealing with userland hooks. Both use indirect syscalls
where required. Make note that the Service Executable cannot be executed
directly like general executables. The Service sxecutable only works with
Service Control Manager as it only has the ServiceMain entrypoint instead of
something like the int main(). This is made to make it less susceptible to
antivirus sandboxes. Both, the DLL and Service Executable contain the same raw
shellcode that is returned when you generate the RtlExitUserThread shellcode and
use indirect syscalls to execute the shellcode. The entrypoint for the DLL is
main, and can be executed using rundll32 as:
rundll32.exe badger.dll,main
Riot Control
Riot Control provides a unanimous command-line interface where an operator can
send commands to multiple badgers simultaneously via a single console.
www.bruteratel.com 24
Pivot Graphs
Pivot graphs display various pivot badgers in a tree format. This graph can only
be exported in HTML format and does not provide any interaction with the
badgers.
KillSwitch
Listeners provide a functionality to run exit_process command on multiple
badgers. It can be activated on a listener by right clicking a listener and
selecting Activate KillSwitch.
www.bruteratel.com 25
WebHooks
Webhook in Brute Ratel is a method of altering the behavior of a Brute Ratel
listener with custom callbacks. These callbacks may be maintained, modified, and
managed by operators of the BRc4. The BRc4 listeners support webhook for all
types of Badger comms. This can be enabled by right-clicking a listener and
selecting the Webhook->Enable option.
Webhook forwards the badger’s output to an operator provided host. When the
Enable option is selected, the operator has to select the type of data they want
to receive. In the below example the data will be forwarded to
https[:]//172.16.219.1:8081 for new badger notifications, as well as a copy of
every output of commands received by the badger.
#!/usr/bin/python3
import threading
www.bruteratel.com 26
from datetime import datetime
from http.server import HTTPServer, BaseHTTPRequestHandler
import ssl
import sys
import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
LHOST = "0.0.0.0"
LPORT = 8081
class Stager(BaseHTTPRequestHandler):
def _set_headers(self):
self.send_response(200)
self.send_header("Content-type", "text/html")
self.end_headers()
def do_GET(self):
return "404 Not Found"
def do_POST(self):
postData = ((self.rfile.read(int(self.headers['content-length']))).decode('utf-8'))
print("[+] Data Received:", postData)
return "200 OK"
def main():
if (len(sys.argv) < 3):
print("Usage:", sys.argv[0], "<certfile> <keyfile>")
return
currtime = (datetime.now()).strftime("%d/%m/%Y %H:%M:%S")
print(f"[+] {currtime} Starting external c2 server on {LHOST}:{LPORT}")
server = HTTPServer((LHOST, LPORT), Stager)
server.socket = ssl.wrap_socket(server.socket, certfile=sys.argv[1], keyfile=sys.argv[2],
server_side=True)
thread = threading.Thread(None, server.serve_forever)
thread.daemon = True
thread.start()
thread.join()
if __name__ == "__main__":
main()
This script listens on 0.0.0.0:8081 and prints the data via webhook. Once a new
badger connects to the server, its initial access information is sent to the
webhook.
After the initial request, further data will only contain the badger ID, the
output of commands, and the main command for the respective badger.
www.bruteratel.com 27
The output is received in the base64 format so that an operator can either
decode it, or forward it to Elasticsearch-Kibana or any other database for
further analysis.
Profiles
Profiles in Brute Ratel are a set of JSON blocks that can configure various
features in the Ratel server. The following types describe the profiles present
in the Ratel server.
Payload Profiles
Payload profiles provide a variety of options to configure and build badgers.
These configurations work independently of the Listener Profiles. This means an
operator can edit, delete, or create new payload profiles and use them
dynamically during process injection, profile migration or to create new
shellcode, DLL, or Service Executables from them. An operator can also store
profiles for their backup Command and Control server in the current C2 and use
them to inject the backup-c2’s profile directly in the current payload, thus
allowing an operator to switch C2s without the need to drop a file on disk. To
add a new profile, select C4 Profiler->Profiles->Payload Profiler and then click
on the Add Profile button.
www.bruteratel.com 28
Here an operator can select between adding a new profile, editing or deleting an
existing one, or generating x86/x64 badgers from that profile. There are 4 types
of payload profiles.
HTTP/HTTPS: The HTTP profile takes in the same type of configuration as that of
the HTTP listener. The fields are identical except there is no information
required for building the listener because the payload profiles are just used to
build payloads and are not bound to any listeners. An operator can create
payload profiles for any other Ratel server, and build payloads from them,
perform injection, or use them to switch profiles. The profiles can also be used
alongside the ‘psexec’ command to dynamically generate and run service
executables on a target host.
The below table describes the key-value pair to generate a Payload JSON profile
www.bruteratel.com 29
override the default proxy-aware settings
proxy_user string Proxy server’s username Yes
proxy_pass string Proxy server’s password Yes
obfsleep string Specifies the obfuscation strategy for badger during No
sleep. Options are: APC, Pooling-0 or Pooling-1
append string Data to be appended to the badger’s post request Yes
append_response string Data to be appended to the server’s response Yes
prepend string Data to be prepended to the badger’s post request Yes
prepend_response string Data to be prepended to the server’s response Yes
empty_response string Data sent by the server to indicate that there are no Yes
commands in queue
request_headers object Headers to be added to the badger’s request Yes
DOH (DNS over HTTPS): Same as HTTP Profile, but for DOH.
The below table describes the key-value pair to generate a Payload JSON profile
www.bruteratel.com 30
obfsleep string Specifies the obfuscation strategy for badger during No
sleep. Options are: APC, Pooling-0 or Pooling-1
request_headers object Should contain "Content-Type": "application/dns- Yes
message"
SMB: The SMB profile can connect to other badgers over Named Pipe. Unlike TCP
badgers which perform a reverse connection, the SMB badger starts a named pipe
and waits for another badger to connect to the named pipe. Named pipes can be
connected using the pivot_smb command. Named pipes use Windows access tokens for
authentication, but this is disabled for SMB badgers. This means in order to
connect to a remote named pipe, an operator can use any badger instead of
needing a privileged one.
The below table describes the key-value pair to generate a Payload JSON profile
The below table describes the key-value pair to generate a Payload JSON profile
www.bruteratel.com 31
Command Profiles
Command profiles, also called as command registries can add custom commands to
the badger. These profiles lower the overhead of the operator to type in the
same commands with paths over and over again. Below are the command profiles:
Object File Registry: The register_obj profile can add a Badger Object File
(BOF) as an internal command to Brute Ratel. These BOFs are executed using the
coffexec command within the badger but are stored in the server’s memory. This
profile requires the name of the command which an operator will execute the BOF,
as the main key (boftest64 in this example). Each command can contain several
properties to further define its type. The arch field describes the architecture
of the object file. The filepath describes the path where the BOF is stored
which is relative to the Ratel server. The description field shows the text
shown to the operator within the commander when the operator types help
boftest64. The mainArgs define the compulsory arguments and the optional defines
the optional arguments for the command. The example field is a hint for the
operator on how the command runs. The minimumArgCount defines the minimum number
of arguments required for the command to run. If the minimum argument is set to
2, and the command is run without any arguments, it will return the help
information for the command, instead of running it. The artifact field should be
WINAPI.
"register_obj": {
"boftest64": {
"arch": "x64",
"file_path": "server_confs/bofs/obj/decltest64.o",
"description": "Sample BOF file to show x64 capabilities",
"artifact": "WINAPI",
"mainArgs": "NA",
"optionalArg": "NA",
"example": "decltest64",
"minimumArgCount": 1
},
"boftest86": {
"arch": "x86",
www.bruteratel.com 32
"file_path": "server_confs/bofs/obj/decltest86.o",
"description": "Sample BOF file to show x86 capabilities",
"artifact": "WINAPI",
"mainArgs": "NA",
"optionalArg": "NA",
"example": "decltest86",
"minimumArgCount": 1
}
}
www.bruteratel.com 33
"file_path": "server_confs/sample_profile_pe/InternalMonologue.exe",
"description": "Runs InternalMonologue C# executable",
"artifact": "WINAPI",
"mainArgs": "NA",
"optionalArg": "NA",
"example": "monologue",
"minimumArgCount": 1
}
}
DLL Registry: The register_dll profile can add a reflective DLL as an internal
command to Brute Ratel. These DLLs are executed using the loadr command within
the badger but are stored in the server’s memory. This profile requires the name
of the command in which the operator will execute the DLL, as the main key
(boxreflect in this example). Each command can contain several properties to
further define its type. The arch field describes the architecture of the DLL.
The filepath describes the path where the DLL is stored which is relative to the
Ratel server. The description field shows the text shown to the operator within
the commander when the operator types help boxreflect. The mainArgs define the
compulsory arguments and the optional defines the optional arguments for the
command. The example field is a hint for the operator on how the command runs.
The minimumArgCount defines the minimum number of arguments required for the
command to run. If the minimum argument is set to 2, and the command is run
without any arguments, it will return the help information for the command,
instead of running it. The artifact field should be WINAPI. The replace_str
field replaces strings present in the DLL with the specified hex bytes. This can
be helpful to avoid YARA rules.
www.bruteratel.com 34
"register_dll": {
"boxreflect": {
"arch": "x64",
"file_path": "server_confs/sample_profile_pe/boxreflect.dll",
"description": "Loads a test reflective dll message box",
"artifact": "WINAPI",
"mainArgs": "NA",
"optionalArg": "NA",
"example": "boxcheck",
"minimumArgCount": 1,
"replace_str": {
"boxit": "\\x00\\x00\\x00\\x00\\x00",
"!This program cannot ": "\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\
x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00",
"be run in DOS mode.": "\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\
x00\\x00\\x00\\x00\\x00\\x00\\x00"
}
}
}
Autorun Profiles
Ratel server can automate initial command execution for badgers using the
autoruns profile. Commands added to the autoruns profile will be auto-executed
on every badger whenever they connect for the first time. This profile can also
be created from the Commander by selecting C4 Profiler->Autoruns, or by loading
their JSON profile from C4 Profiler->Profiles->Upload Autoruns Profile via the
profile below.
"autoruns": [
"sleep 0",
"set child werfault.exe",
"pwd",
"userinfo"
]
Clickscript Profiles
Click Scripting is a feature that allows operators to automate the execution of
grouped commands. Unlike the Autoruns feature which lets an operator to auto-
execute several commands on the first connection of badger, Click Scripts are a
list of multiple commands which can be chained together to execute one command
after the other at any time. This helps with automated execution of commands
belonging to different Tactics and Techniques of MITRE ATT&CK which can be
chained together during a Purple Team engagement. Below is an example of some
discovery-based commands which are grouped into a single Click script called
‘Discovery’. This script can also be created from the Commander by selecting C4
Profiler->Clickscripts, or by loading their JSON profile from C4 Profiler-
>Profiles->Upload Command Profile. To run these Click scripts, right-click a
badger, load a Click script and click the run button.
"click_script": {
"Credential Dumping": [
"samdump",
"dcsync"
],
"Discovery": [
"userinfo",
"pwd",
"ipstats",
"psreflect echo $psversiontable",
"net users",
"scquery"
]
www.bruteratel.com 35
}
Once this is added, an operator can load the clickscript from the badger’s
context menu in the badger’s tab (right-click a badger), and then select the
Load Click Script option. The below figure shows the loaded Click Script, which
can be executed by selecting the Play button next to the badger’s ID. Each Click
Script can contain any number of commands, and an operator can use it to build
playbooks for purple teaming.
Hosting Files
Files can be hosted on the Brute Ratel HTTP listeners by right-clicking on a
created listener and selecting Listener Actions->Host File. Mime types can also
be customized for the data that is to be returned upon request.
www.bruteratel.com 36
Root Page Changer
The root page of all HTTP listeners can be customized using C4 Profiler->Change
Root Page. This opens a dialog box where a user can enter HTML/JavaScript which
will be rendered on the root page of all listeners. However, it works
differently for the badger. The Listeners are configured in such a way that it
automatically identifies whether the request has been sent by a
person/automation tool or a badger. After differentiating the request, it parses
the badger’s response and searches for an authentication key. If it doesn’t have
any, then it would return a 404 not found. This works well in hiding your
badger’s server behind a legitimate HTML page.
PsExec Configuration
The PsExec feature of BRc4 is partially similar to Microsoft’s PsExec. It
creates a service on a given system and starts it using Remote Procedure Calls
(RPC). But unlike Microsoft’s PsExec which uses CreateProcess API to pipe
cmd.exe over SMB, BRc4’s PsExec service contains a shellcode blob for a payload
www.bruteratel.com 37
profile provided during the execution of PsExec. This payload can either be SMB,
DOH, HTTP, or a TCP profile and doesn’t necessarily limit you to just SMB
badgers. One of the most important OpSec considerations during lateral movement
is to keep badger disguised as a legitimate service. Several PsExec options such
as service name, description, service executable name, and the type of payload
to execute on the remote host are customizable. These can be configured by
selecting C4 Profiler->PsExec Config.
This PsExec information can also be added via JSON profile as:
{
"psexec_config": {
"psexec_svc_desc": "Manages support for Windows Apps from Microsoft Store.",
"psexec_svc_name": "TransactionBrokerService"
}
}
www.bruteratel.com 38
TCP Listeners
A badger can start a TCP listener where TCP badgers can connect from different
hosts for pivoting. This can be started using the pivot_tcp command. All active
TCP listeners can be viewed by selecting Server->TCP Listeners.
Credentials
Pre-existing credentials (breached credentials) or credentials harvested during
red teams can create Windows Access Tokens for lateral movement. They can be
created using the make_token command or added to the server using a profile or
Commander. Once added, an operator can select this from the Commander to create
a local or network token for lateral movement using the right-click context
menu. To add a credential, an operator can select Server->Add Credentials.
Credentials can also be imported using a CSV file. A quick sample of this CSV
would be (make note of the headers):
creduser,credpass,creddomain,crednote
administrator,admin@123,jupiter.corp,Domain Admin
dev,password@123,jupiter.corp,Domain User Local Admin
dev-user,password,localhost,Local Admin
These credentials are also saved in the JSON profile, or can be imported via a
JSON profile in the following format:
www.bruteratel.com 39
{
"credentials": [
{
"creddomain": "bruteratel.corp",
"crednote": "Domain Admin Password",
"credpass": "admin@123",
"creduser": "administrator"
},
{
"creddomain": "jupiter.solar.corp",
"crednote": "Domain Admin Password",
"credpass": "jupiter@123",
"creduser": "administrator"
}
]
}
Watchlist: This is the main server log that an operator also sees in the
terminal and the Commander event logs.
Badger directories: All badger logs are rotated every 24 hours. At 00:00
midnight, the current day’s directory is created and new logs are stored in the
current day’s directory. This is why a badger’s terminal is reset after 00:00,
because the previous day’s logs aren’t loaded to the terminal in Commander. This
is done to preserve the old logs and to avoid cluttering the user interface with
too much data which can make the Commander laggy. All badger logs are stored
under their respective ID names (b-0.log, b-1.log...)
Upload/Download Logs: All upload and download logs are stored in the base
directory similar to the watchlist logs.
DeAuth/Web Logs: All unauthenticated badger and weblogs are stored in their
respective day’s directory similar to that of badger logs.
All logs can be viewed by selecting Server->View Logs. This will open a new tab
next to Downloads, which can view the log files in the scratchpad.
www.bruteratel.com 40
Operator Activity
Commander provides detailed logs of all the commands executed by the user
alongside the respective MITRE tactics and techniques for audit purposes. This
contains short commands, full commands, time, and MITRE information as to when
the command was executed and how many times an operator executed a specific
command. You can access the activity log by selecting Server->Operator Activity.
You can filter out a specific operator by selecting the operator from the drop-
down menu and exporting the logs into CSV.
www.bruteratel.com 41
MITRE Graphs
All commands executed by the badger can be viewed in a graphical format for
reporting purposes along with their MITRE tactics and techniques. An operator
can export this graph in HTML format for either only the commands they executed
or for all commands present in the badger by selecting Server->Export MITRE Team
Graph (HTML) or Server->Export BRc4 MITRE Graph (HTML).
Graph Sample
Shortcut Keys
Below are a list of shortcut keys that can be used in Commander:
www.bruteratel.com 42
Listener Tab Alt+1
www.bruteratel.com 43
Badger Core
Badger is the main implant of Brute Ratel for remote access with Unicode
support. Badgers support egress over HTTP, HTTPS, DNS Over HTTPS, SMB, and TCP.
SMB and TCP are peer-to-peer connections for inter-network communications.
Badgers are asynchronous and multi-threaded. It will connect back to the Brute
Ratel Server every few seconds/minutes/hours as configured with the sleep and
jitter values, fetch tasks queued on the Ratel server, run them, and return a
response. All Badgers communicate with each other and to the server using custom
encryption. The key for the encryption can be added to the JSON profile as:
{
"comm_enc_key": "WeiJeeWeiCufae2y"
}
{
"badgers": {
"b-0": {
"b_bld": "18363",
"b_c2": "https://192.168.0.142:443",
"b_c2_id": "Primary-Https",
"b_cookie": "QQD7QGSMCCTV66OU5C8GAQTQNTU8H7MD",
"b_h_name": "DESKTOP-G15FRLS",
"b_l_ip": "192.168.0.142",
"b_p_name": "Z:\\documents\\badger.exe",
"b_pid": "7268",
"b_seen": "09-05-2021 09:14:19",
"b_uid": "vendetta",
"b_wver": "10.0",
"is_pvt": false,
"pipeline": "Direct",
"pvt_master": "",
}
}
}
Most shellcodes are assembly wrappers over a reflective DLL. Brute Ratel however
does not contain a reflective DLL. It contains a custom PE without any export or
import address tables. This PE cannot be loaded by a defender’s custom loader
because it is heavily dependent on Brute Ratel’s shellcode loader which sets up
various variables before executing the PE. The shellcode loader is also
responsible for identifying if the badger is being executed within a debugger,
setting up a custom call stack, unhooking the EDR, extracting pointers from PEB
of the current process, and more before executing the encrypted PE (henceforth
called badger core). Badger comes prebuilt with a variety of operational
security features, a lot of which reside within the initial shellcode before it
executes the badger core. The following section describes the various
operational security considerations built-in within Brute Ratel alongside the
commands that can be used for post-exploitation activities.
www.bruteratel.com 44
Thread Stack Encryption Yes Yes Yes
Badger Heap Encryption Yes Yes Yes
Secure Free Badger Heap for Volatility Evasion Yes Yes Yes
Advanced Module Stomping with PEB Hooking Yes Yes Yes
Unhook EDR Userland Hooks and Dlls Yes No No
LoadLibrary Proxy for ETW Evasion Yes No No
Unhook DLL Load Notifications Yes No No
Hardware Breakpoint for AMSI/ETW Evasion Yes Yes Yes
Reusing Virtual Memory For ETW Evasion Yes Yes Yes
Reusing Existing Libraries from PEB Yes Yes Yes
In-Memory RDLL Execution Yes Yes Yes
In-Memory PE Execution Yes Yes Yes
In-Memory BOF Execution Yes Yes Yes
Module stomping for BOF/Memexec Yes Yes Yes
In-Memory Dotnet Execution Yes Yes Yes
Network Malleability Yes Yes Yes
Built-In Anti-Debug Features Yes Yes Yes
Syscalls are represented by numbers. These values change with major version
upgrades on Windows. Syscalls are executed by a wrapper function in ntdll.dll
called NTAPI. NTAPIs are present in the Export Address Table of ntdll.dll so
that other DLLs can load ntdll.dll and call the required function. APIs or
exported functions present in other Windows DLLs are wrappers for code which
eventually call NTAPI from ntdll.dll. These are called Windows API or WinAPI.
When you execute a function, for example from Kernel32, it will perform the
required stack and heap allocations for variables and structures before calling
its respective NTAPI which then calls the syscall instruction. Below is the most
basic example of a transition of CreateFileA WinAPI in kernel32.dll to Syscall:
www.bruteratel.com 45
The below figure shows how an NTAPI wraps around a syscall value for Windows 10
2H22.
The above figure shows that the syscall number for NtCreateFile is 0x55. Several
security solution softwares often apply a jump instruction (trampoline hook)
here, so that when an implant executes a generic Windows API call, it would get
trapped over here when it eventually lands to ntdll.dll. The below figure shows
a jump instruction from a well-known security solution softwares which traps
WinAPI and NTAPI calls.
Brute Ratel contains a miniature debugger which was introduced in release 0.9
for syscall tracing. This feature pauses the current execution when any syscall
is made, eg.: NtOpenProcess, NtReadVirtualMemory, and so on, it traces the jump
calls made by NTAPI and follows the trampoline jump instructions added by the
EDR. Post finding the jump, it identifies the opcodes manually and traces the
exact location of the syscall which is either stored in the EDR’s memory or
sometimes in the memory of a random DLL which was loaded by your process. Once
this syscall value is found, the badger loads this value in the RCX register,
creates a rop gadget to return to a custom location on the stack, and then jumps
to the syscall pointer (0x0F05). This way, when the syscall is executed, the
return instruction (0xc3) in the ntdll.dll points to our custom stack pointer
that we added. Several EDRs also place a hook in the kernel to check if the
syscall is made from a reflective DLL’s RX region instead of ntdll.dll. Using
indirect syscalls, these can be bypassed.
While building this technique, it was found that some EDRs store the syscalls in
a READONLY region with guard pages enabled, whose memory permissions are changed
by the EDR’s DLL itself. If Badger finds any such pages during its initial
execution, it will automatically point itself to the guard page removal code in
the EDR’s DLL, execute those instructions, and then point the RIP to the syscall
found, making sure that the execution is performed at the place where the EDR
saved the original instructions instead of modifying and removing the syscall
hooks. It auto-manages the stack and the registers to call the syscall while
preserving the existing information in the registers. All of this was done in
order to avoid tampering with the EDR DLL’s memory or removing the hooks since
removing the hook itself is monitored sometimes by the EDR. Brute Ratel employs
these techniques by default in both stealth and default modes and does not
www.bruteratel.com 46
require the operator to enable anything manually. However, if stealth mode is
used alongside module stomping, then indirect syscall is disabled as the stack
frame would by default be legitimate, unlike the direct syscall technique.
www.bruteratel.com 47
Example of Thread Stack Duplication
Every function call made in an unmanaged application has a valid stack frame.
This stack can contain information about a thread and the function in which it
is being executed. Whenever a new thread is created, a new stack is allocated.
This stack frame contains the base address from where the function was executed,
the variables passed on as arguments, variables allocated on the stack, the
return address, and more. All this information on the stack makes a valid stack
frame. A thread is always started by the kernel using NtCreateThread or similar
NTAPI/Syscall like RtlUserThreadStart. This means a thread will always start
from ntdll.dll. In our case, this NTAPI is RtlUserThreadStart.
RtlUserThreadStart calls BaseThreadInitThunk from kernel32.dll and then other
respective functions are called. Below is an example of a valid stack from
Process Hacker.
www.bruteratel.com 48
Make note how the entrypoint which is also a valid address on disk
(notepad.exe+0x23f40). Legitimate executions from disk will always be in this
way except for a few odd managed dotnet executables. However, the caveat here is
that if a reflective DLL or shellcode is executed, the addresses for these
memory locations do not back to disk, as they are manually allocated by the
operator’s code. Also note that since the shellcode/reflective DLL is executed
in memory, the entrypoint (notepad.exe+0x23f40), would also not be backed to
disk. Below is an example of Cobalstrike’s beacon v/s Brute Ratel.
Brute Ratel:
www.bruteratel.com 49
The reason why this is important is that EDRs like Elasticsearch use Event
Tracing (ETW) to capture the stack telemetry when a syscall reaches kernel mode.
If the stack belongs to an operator-allocated region that has a bad stack or bad
entrypoint and is not backed by disk, the thread will be instantly killed by the
EDR. Badger’s sleep masking technique prevents this from happening. There are
three main IOCs here that Sleep masking evades: the initial entrypoint, and the
stack frame, and the RX region. The RX region is converted to RW during sleep
and encrypted to avoid memory scans. The entrypoint of the thread is only
spoofed when you build a payload with the type RtlExitUserThread.
WaitForSingleObject badger should be used with asynchronous procedure calls
(APC). The RtlExitUserThread shellcode of badger exits the thread created by the
operator after spawning another thread with a clean stack and entrypoint. Thus,
the thread handle return by the shellcode of RtlExitUserThread cannot be used to
wait. Since the primary thread exits in this case, it is not suitable to be run
with APC injections as that can exit or crash a process. It is recommended to
use the WaitForSingleObject shellcode for such scenarios. More information on
this can be found here and here.
www.bruteratel.com 50
The entrypoint of all threads should now look as follows:
www.bruteratel.com 51
PROCESS ATTACH/THREAD ATTACH events within the process, this Dllmain will
not be called.
2. ImageDLL flag in PEB is marked as false. This means DLL was loaded as an
Exe and not DLL.
These anomalies are usually enough to detect module stomping in any other C2s
apart from Brute Ratel. Another easy way to detect module stomping is to compare
the .text region of the DLL on disk and the one in the memory of the process as
they would be different due to the memory region being stomped with the
shellcode.
www.bruteratel.com 52
indirect calls should be called from a valid start address and not from the
middle of any code from any .text region. This information about the valid
function locations is stored in the Characteristics region of each section in
the PE which can be read using a CFF explorer by doing bitflag checks. However,
this is a bit trickier than expected. Ideally, if we just copy our code to the
entrypoint of a stomped DLL, it should work because the entrypoint is a valid
start of a function. Let's take an example of staged Metasploit shellcode which
is 512 bytes. If our entrypoint code (in DLL) is of, say only 1000 bytes, and
our shellcode that we copied is of 512 bytes (Metasploit), our staged code will
simply allocate new memory, copy reflective DLLs to the newly allocated region
and execute them. This is not operationally safe, because we are indirectly
allocating a new region. Thus most POCs you see with Metasploit will work (as
POC only) but do not benefit in terms of evasion for the final stage. Because,
unlike POCs, to perform proper evasion, we have to make sure our full PE code is
backed by a valid .text section on disk. This means we cannot use staged code,
and our reflective DLL or second stage should be within the .text region and it
should start from a valid call target to avoid CFG.
All C2s use some sort of PE or reflective DLL for stageless payloads and these
are usually more than 150-200kb as they might contain several post-exploitation
code, unlike staged code. So what happens if our .text region is say 300kb, the
entrypoint code is of, say only 1000 bytes, and our shellcode that we copied is
a 200 kb reflective DLL? We end up overwriting another function in the .text
region. If we perform any type of threaded calls from this region, especially if
the process is a CFG-enabled process (which most of the Windows processes are),
we end up calling ntdll!LdrpDispatchUserCallTarget which will check the indirect
call location and the bitflags enabled for that location. The ntdll!
LdrpDispatchUserCallTarget is an internal function of ntdll.dll (notice the p in
Ldrp) which takes an argument in the RCX register. This argument is the address
region that needs to be vetted for invalid call targets. If the region from
where the call is originating is invalid, ntdll!LdrpDispatchUserCallTarget calls
RtlFailFast2 with a STATUS_STACK_BUFFER_OVERRUN exception which kills our
process instantly. This means, if we want to evade CFG, we have to disable CFG
on our stomped DLL’s executable region. Below is the callstack for a thread
which called LdrpDispatchUserCallTarget.
1. Badger deletes all of its regions from the memory of the process while
sleeping and restores the original DLL’s buffer till the sleep is
complete. This is done alongside stack spoofing, stack encryption, and
heap encryption to avoid all traces of the badger and its data while
sleeping. Thus if anyone scans the stomped module to perform a comparison
of on-disk and in-memory regions while the badger is sleeping, it would
look the same. When the badger is not sleeping, all of the evasions still
work, except now the .text region of the DLL contains the badger’s
shellcode.
www.bruteratel.com 53
2. Badger also uses a custom hook to The PEB LDR module to reflect the
necessary changes to avoid detections for entrypoint and DLL Flags which
can also be seen in this video.
For people interested in using their own custom module stomping technique, the
commands set cfg and clear cfg have been added to disable or enable Control Flow
Guard. This is not required for the badger, but if you want to create a process
and perform module stomping injections with your own post-exploitation toolkit,
then CFG can be disabled using these commands.
Make note that even with all these evasions, it’s an operator who has to be
careful with the module they want to stomp. Overwriting sections of bad DLLs can
lead to a process crash, especially if the DLL you stomped is being utilized by
some other module/code in your process. The module stomping feature can be
enabled via Payload Profiles or during the creation of a listener. Make note
that module stomping is disabled for DLLs generated by the Commander. Because if
a DLL loads a module and calls its DllMain, this Dllmain (now badger) will call
LoadLibrary to load other DLLs. But since this Dllmain will be under loader
lock, you cannot load other DLLs. Thus module stomping will not directly work
with DLLs or DLL sideloads. You would have to be a little creative on this part
to make it work, to make sure loader-lock doesn’t happen. Staging also supports
module stomping. This means you can stomp a stage yourself, and let the stage
stomp your stageless code into another stomped module.
www.bruteratel.com 54
Page Guards from Sentinel One
www.bruteratel.com 55
the API call is originating from. If the originating region is from a user-
allocated RX/RWX region, the process would be eventually terminated after
sending in the telemetry to the EDR’s console. Most generic reflective DLLs will
be killed at this point which called LoadLibraryA to load DLLs into memory.
Another minor issue here would be the trap from ETWTI sensors which can check
the stack frame to identify where the call is originating from. If the call made
to NTAPI with the spoofed argument itself is originating from user allocated
RX/RWX region, unbacked by a module on disk, that itself triggers an anomaly for
certain EDRs capturing stack telemetry via ETWTI or even the user-land hooks in
this case. There are no known public techniques that evade such detections
simultaneously on user-land and the kernel. Upon further research, it was
observed that the EPROCESS block of a process actually stores various regions of
ntdll.dll spread across various structures. If one can find this region and its
offset, it becomes extremely easy to find the legitimate ntdll’s base address in
memory, and then further utilize it to extract other metadata of ntdll,
kernel32, and kernelbase. The EPROCESS information can be dumped from Windbg in
the kernel mode using kdextensions.
If all of the previously mentioned traps are bypassed, there still resides an
issue of extracting the correct NTAPI function pointers from the EAT as the EAT
of ntdll will also be hooked. Walking the EAT and extracting the function
pointer leads down a rabbit hole since all the original function pointers are
overwritten with an address belonging to the Page Guarded region of the userland
DLL, thus executing another hit to the trap. However, this can be evaded by
unhooking the EDR’s DLL before extracting information from the EAT.
www.bruteratel.com 56
Comparative analysis of hooked ntdll.dll v/s original ntdll's EAT
Both staged and stageless stealth shellcodes of the badger unhook the EDR’s DLL
as well as use custom techniques to find the address of ntdll.dll into memory.
Make note that the stealth shellcode only works on x64 versions of Windows
except on Server 2012. For this reason, the default version still exists which
will still evade most traps on x86 and x64 except the unhooking of the DLL. Once
the EDR’s DLL is unhooked, an operator should be able to use all NTAPI and
WinAPI calls without having to worry about any hooks in the EAT or jump
instructions in the RX region of the system DLLs.
www.bruteratel.com 57
as soon as the task is complete. If these are not cleared, then the thread which
executes the breakpoint can be pretty CPU intensive. Badger uses carefully
crafted HWBP to only enable them just before the assembly is loaded and the
debug registers are cleared as soon as the assembly is unloaded and the VEH is
removed. This video provides a brief explanation of the use of Hardware
breakpoints for evading detections. This is enabled by default in the
sharpinline command, and also for several other commands.
www.bruteratel.com 58
Remote Memory Allocation and Thread Execution Techniques
In-Memory PE Execution
Command: memexec
Badger can run any unmanaged executables compiled in Clang or MingW GCC/G++
within its own memory. This avoids process creation events or creating new
processes. Some executables call ExitProcess when they return, and the
entrypoint of the executable is mainCRTStartup from msvcrt.dll instead of int
main() or void main(). This means that badger should be capable of handling the
Exits and it should not exit itself when the in-memory executable process
returns. Badger accomplishes this task with the help of hardware breakpoints.
Make note that GUI executables are not officially supported, and the executable
should be compiled in MingW or Clang. If Visual Studio is used to compile the
executable, make note that changing the library type is required. This can be
changed from MFC to standard libraries in the Visual Studio configuration as
Project Properties-Configuration Properties->Advanced->Use of MFC Change to Use
Standard Windows Libraries. The memexec command can run any console executable
in memory and return the output of the executable using a custom in-proc-
console-reader. Below is the screenshot of mimikatz and handles64.exe from
Sysinternals toolkit.
www.bruteratel.com 59
Executing mimikatz.exe coffee command in memory
www.bruteratel.com 60
stomping support for BOF, zeroing out BOF heap and stack before exiting its
thread, hooking various ETW APIs, and more.
The coffexec command parses the object file provided by the operator and patches
the exported functions on the fly with the internal APIs of Badger and Windows
DLLs. This makes the port of existing Cobaltstrike BOFs to Brute Ratel extremely
easy. Let’s take the following Cobaltstrike’s BOF as an example which was taken
directly from their website.
#include <windows.h>
#include <stdio.h>
#include <dsgetdc.h>
#include "beacon.h"
NETAPI32$NetApiBufferFree(pdcInfo);
}
As can be seen in the code above, the entrypoint for the COFF file for
Cobaltstrike is ‘go’. In the case of Brute Ratel, however, the entrypoint is
coffee. Below is the code for Brute Ratel’s BOF (Badger Object Files).
#include <windows.h>
#include <stdio.h>
#include <dsgetdc.h>
#include "badger_exports.h"
There’s not much difference except for the internal API calls (BeaconPrintf for
Cobaltstrike and BadgerDispatch for Brute Ratel). The below figure shows the
executed output of the COFF file:
Post compilation, the BOF can be executed using the coffexec command.
www.bruteratel.com 61
BOFs do not require any RWX region to work and they get executed like any other
internal function of the badger. Below are a few other API calls which are
available in this release that can be used in BOFs. These can be found in the
badger_exports.h file as well which you would need to include in your COFF
generating C file.
BadgerAtoi: Converts an ascii value to an integer similar to atoi, but does not
call the atoi from msvcrt.dll
www.bruteratel.com 62
BadgerFree: Frees allocated heap
A brief example on the usage of all the above APIs is provided in the
server_confs/bofs directory in the Brute Ratel package.
This video provides a brief overview of how this feature works. The sample BOF
injection templates are added to the server_confs/bofs directory in the Brute
Ratel package. The clear coffargs command clears all file buffers stored in the
memory of the badger configured for the coffexec command.
www.bruteratel.com 63
Module stomping for BOF/Memexec
Command: set/get/clear module_stomp
The Advanced Module Stomping technique within the badger also supports coffexec
and memexec. Before you execute a BOF (coffexec) or a PE (memexec) in memory,
you can configure a separate module to stomp using the set module_stomp command.
This module name can be fetched or cleared using the get module_stomp or clear
module_stomp command. Once a module is configured, all BOFs and PE will be
automatically mapped to the stomped module region. This region’s original DLL
content will also be restored once the BOF or the PE has completed execution.
Similar to the module stomping of the badger, the stomped DLL’s PEB is also
patched here to avoid detections. Make note that the module selected for
stomping must have a .text section larger than or equal to, the size of the PE
or the BOF, else the stomping will fail with the error
ERROR_ILLEGAL_DLL_RELOCATION. coffexec and memexec will also check if the module
stomped is required by the PE or the BOF’s Import Address Table. If it is, then
the stomping fails again and prevents the badger from crashing as stomping a
module required by your PE or object file can raise invalid address exceptions.
www.bruteratel.com 64
The process injection options for the sharpreflect command can be configured
using the set child, set parent, set dllblock, set malloc, and set threadex
commands.
www.bruteratel.com 65
fundamentals towards building your own External C2. This repository contains the
core logic and the code in C to build your External C2 Connector and the Server.
Below are a few points worth noting before building your Connector and the
Server.
1. SMB or TCP badgers can interact with your External C2 Servers using an
HTTP connector. The Github example uses SMB badger for this.
3. SMB and TCP badgers return output which is encrypted and then encoded in
Hex (earlies base64 for pre-1.6 release).
4. The aim of the HTTP connector is to read this output and reroute it to
wherever the operator needs it to; for eg.: Slack, Microsoft Teams
Channel, Dropbox or even sending data inside an Image blob to file hosting
websites, etc.
5. The connector provided in the example reads and writes the buffer to the
SMB named pipe. It is the duty of the operator to write the remaining code
logic for forwarding it to their own External C2 Server.
6. Make sure the BRc4 Ratel Server receives the full response, as-is from the
External C2 Server. This means if the badger returns an encrypted-encoded
output of 10000 bytes, then it should be sent as-is to BRc4’s HTTPS
Server. The output cannot be in parts because the Ratel Server is only
responsible for receiving the whole output, decrypting the output, and
sending a response back. Ratel server cannot receive partial chunks as it
cannot decrypt them. Decryption needs the full message and not multiple
chunks in separate requests.
◦ Receive SMB Output from the SMB/TCP Badger (the Github example uses SMB
badger)
◦ The External C2 Server should either support Webhooks which can forward
these chunks to an External C2 Handler controlled by the operator, or
the External C2 Handler will have to read this from the External C2
Server
◦ The External C2 Handler should receive the chunked buffer from the
Server, combine all the responses, and send it to the Ratel Server
◦ The External C2 Handler will also have to receive a response from the
Ratel Server and forward it to the External C2 Server. If the response
from the Ratel Server is more than the limited number of bytes the
External C2 Server can accept, then the External C2 Handler will have
to split it into chunks and send it to the External C2 Server
www.bruteratel.com 66
◦ The badger then has to read this response sent to the External C2
Server and forward it to the SMB badger
9. Badger will send a request on the named pipe as per its sleep cycle.
External C2 connectors and servers can be written in any language. The current
example uses C language since it’s easy to convert the connector to a PIC as
explained in my blog here.
Badger Interaction
An operator can interact with the Badger using the right-click context menu from
the badger’s Tab or from the Badger’s Terminal. This context menu provides
various options to interact with badger in a graphical way.
www.bruteratel.com 67
Load
This option loads the badger’s terminal over the Watchlist widget.
Clear Cmd-Q
This option clears all commands in the queue on the ratel server that is waiting
for the badger to check in.
Arsenal
This option provides a graphical interface for a few commands of badger for the
operator’s ease of use. These commands are LDAP Sentinel, Profile Switcher,
Process Manager, File Explorer, and Crypt Vortex.
www.bruteratel.com 68
LDAP Sentinel
This option can enumerate various attributes of an object from the Active
Directory environment. This user interface uses the command sentinel at the
backend and provides a robust interface for the operator to customize the LDAP
queries. All LDAP queries evade ETW in the userland. An operator can select the
type of enumeration (User, SPN, GPO, Computer) required, and either write custom
LDAP queries or build one by selecting the ‘prebuilt query’ option by selecting
specific attributes. An operator can also provide a separate domain from the
cross-domain enumeration.
Switch Profile
This option provides the capability to switch the badger’s profile on the fly.
An operator can add a custom profile for a backup C2 infra in case the primary
infra gets detected by the blue team. Using this option, an operator can stay in
the same badger, and just change the network comms with a totally different
domain/uri/redirectors/headers etc.
www.bruteratel.com 69
Process Manager
This option displays active processes in the badger’s host like a task manager.
An operator can also filter out a process by typing its name next to the input
box in the Grab Token button. This process manager is not auto-updated, and the
operator has the press the Refresh button to update the process information.
www.bruteratel.com 70
File Explorer
This option provides a graphical user interface to view the file system of the
badger’s host. An operator can navigate local or remote directories over SMB. To
access a remote host over SMB, the operator can enter the path in the Enter Path
field. Files/Folders can be searched/filtered using the Search file.../Search
folder... field. An operator can also interact with the files and folder by
right-clicking the files with a limited set of capabilities such as copying the
name, downloading or deleting the file, uploading files to a folder, creating
new directories etc. If a file is deleted, the path is not auto-refreshed and
the operator has to double-click the same folder on the left-hand side column to
refresh it. Navigated directories from history show up with a Red vertical bar
as can be seen in the image below next to the folder’s name. To view files in a
previously navigated folder, just click on the folder’s name and it will
autoload the file names from the commander’s memory.
www.bruteratel.com 71
Crypt Vortex
Crypt Vortex is a ransomware simulation reflective DLL that uses a custom
encryption algorithm to encrypt files. It can encrypt and decrypt files on a
host alongside providing a few options for customization such as recursive
folder encryption support. The encrypt option provides 4 options. The first one
is the encryption key, the second option is the path to encrypt and the third
option is the extension of the file after the encryption completes.
This command also supports an additional optional argument to specify only the
selected type of files you want to encrypt. For example, if you want to encrypt
only Word and Excel files, you can select .docx and .xlsx with comma separation.
Encryption is recursive. So if the entered path contains multiple folders and if
those folders contain more folders, then all the folders will be recursively
encrypted one by one. The below figure shows the directory which contains 4
files. The Crypt Vortex command also returns the status of the encrypted files
and the password used to encrypt them. If you decide at a later time that you
want to decrypt some files, then you can still find the password in the badger
logs.
www.bruteratel.com 72
The below figure shows the encrypted content of a simple text file that looks
like garbage. Once the encryption process completes, the original file is
deleted from the disk. Take heavy caution while running this since it can
heavily damage the host if you don’t know what you are doing.
www.bruteratel.com 73
Load ClickScript
An operator can load an added Clickscript from this option. The below figure
shows the loaded Clickscript, which can be executed by selecting the play button
next to the badger’s ID. Each Clickscript can contain any number of commands,
and an operator can use it to build playbooks for purple teaming.
Remove
This option removes the selected badger and its metadata from the Ratel server.
If the badger checks back in, it will not be able to authenticate with the Ratel
server, and would show up in access denied logs. However, all commands executed
for the removed badgers will still show up in the logs directory.
Export To CSV
This option allows an operator to export various metadata of the badger to a CSV
for reporting. An operator can select from the various options present in the
exporter dialog.
www.bruteratel.com 74
Mark Dead
The badger is marked inactive with a dark red color. This information is also
added to the badger’s profile. If the badger checks in after it’s marked dead,
the color changes to active again. Exited badgers are marked dead by default.
Color
An operator can decide to change the color of the badger’s foreground or
background as per personal preference using a color picker. Below is a quick
example of color changes made to the badger.
Exit Thread
Exits the thread in which the badger is residing. The process stays active.
Exit Process
Exits the process in which the badger is residing. The process is killed.
Badger Commands
Badger provides more than a hundred commands which use Windows API, NTAPI and
indirect syscalls. These commands can perform local or remote host enumeration,
user enumeration, active directory enumeration and more. The help command of
badger returns a detailed output of the required and optional command-line
arguments. It also provides information on configurable commands. The help
output of a command is divided into eight parts:
Supported Commands: The supported commands show if the current command can be
configured by some other commands.
www.bruteratel.com 75
Affected Commands: The affected commands show which other commands will be
affected when you configure the current command.
Artifact: It shows whether the Artifact uses process creation, Windows API or
just raw C code.
Main Argument: The main arguments required for the command to run.
Optional Argument: The optional arguments that can be provided to the command.
Minimum Argument Required: This shows the minimum number of arguments required
for the command to run (the count includes the main argument).
The below list provides brief information on every command present for the
badger.
Process Injection
Brute Ratel provides a variety of commands to configure injection techniques and
process spawning before injection actually takes place. The set command can
configure these tasks.
www.bruteratel.com 76
Command: set/get malloc
Badger has a very powerful set of memory allocation and injection techniques.
These include multiple WinAPI, NTAPI, and direct syscall executions all while
evading the ETW syscall hooks implemented in userland by an EDR. All the
injection techniques support PPID Spoofing, DLL Blocking, and custom child
process. When memory injection is performed, the badger needs to allocate RX
regions in the target process. This command provides the ability to change the
memory allocation technique for process injection. The shinject_ex, loadr,
sharpreflect, psreflect, mimikatz and cryptvortex commands use the malloc
technique configured here. The malloc options are:
Example:
www.bruteratel.com 77
The configured technique can be retrieved using the get malloc command.
0 = CreateRemoteThread (WINAPI)
1 = RtlCreateUserThread (NTAPI)
2 = NtCreateThreadEx (NTAPI)
3 = QueueUserAPC, ResumeThread (WINAPI)
4 = QueueUserAPC, NtResumeThread (WINAPI+NTAPI)
5 = QueueUserAPC, NtAlertResumeThread (WINAPI+NTAPI)
6 = NtQueueApcThread, ResumeThread (NTAPI+WINAPI)
7 = NtQueueApcThread, NtResumeThread (NTAPI)
8 = NtQueueApcThread, NtAlertResumeThread (NTAPI)
9 = NtCreateThreadEx (Obfuscated Indirect Syscalls)
10 = NtQueueApcThread, NtResumeThread (Obfuscated Indirect Syscalls)
11 = NtQueueApcThread, NtAlertResumeThread (Obfuscated Indirect Syscalls)
12 = Remote Procedure Call
Make note that if you plan to execute the badger’s shellcode using any of the
APC technique above, you should use the WaitForSingleObject shellcode instead of
the RtlExitUserThread. The configured technique can be retrieved using the get
threadex command.
www.bruteratel.com 78
The configured process can be retrieved using the get parent command.
www.bruteratel.com 79
Checking this in sysmon, shows us that the spoofed argument was indeed used.
www.bruteratel.com 80
The left figure shows the process with CFG enabled, while the one on the right
shows the process with CFG disabled. More information on CFG can be found here.
Command: suspended_run
This command creates a process in suspended mode. This can be useful to perform
custom remote process injections using BOF or built-in badger techniques.
Command: loadr
This command can load reflective DLLs into a target process. Badger uses a
custom loader to load reflective DLLs. Thus, even if the DLL’s exported
symbol/function name is wiped from the DLL, it will still be able to call the
exported symbol by parsing the PE headers and calling the first function pointer
from the DLL, provided there is only 1 exported function in the DLL. This
command also accepts command-line arguments that can be supplied to the
reflective DLL. The below figure shows boxreflect.dll loaded with a command-line
argument randomStringArgument. Once this DLL gets the argument, it returns
Returning this output output in the badger’s console. Operator needs to
configure the child process to inject using set child command. In this example,
the DLL was injected to searchprotocolhost.exe.
www.bruteratel.com 81
The injection techniques for loadr can be configured using set malloc and set
threadex.
Command: memhook
This command can add custom hooks to various sections of the badger’s memory. It
can overwrite any valid region in memory with the opcodes provided by the
operator, using indirect syscalls. Let’s take the below example. Some open-
source dotnet offensive tools call the function Environment.Exit() from
mscorlib.ni.dll after the execution is complete. However this can be fatal for
the badger as this function can exit the process.
using System;
using System.Collections.Generic;
using System.Reflection;
namespace EnvExit
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Before Exit");
Environment.Exit(0);
Console.WriteLine("This should not print if patch failed\n");
}
}
}
The above dotnet code prints a statement before and after calling
Environment.Exit(). Thus if we patch Environment.Exit() and call it again, we
should not exit the badger process. We can patch this method with a xor rax,
rax; ret to stop C-sharp executables from exiting when the dotnet is loaded in
the current process with the sharpinline command. The dotnet code to extract the
Environment.Exit() address is available in the BRc4 package. This address can be
patched with any user provided opcode. In the below example, it’s over written
with opcodes to return zero in the RAX register, before finally running the
above dotnet code to check if the process still exits.
www.bruteratel.com 82
As can be seen in x64dbg figure below, the memory location is now patched. This
command is extremely powerful as you can manipulate the execution flow of
functions on the fly including patching of syscalls hooked by EDRs at runtime.
Command: phantom_thread
This command can execute a shellcode or reflective DLL on a target process using
a custom injection technique. In order to use this command, an operator has to
first identify a thread in a process that is in an Alertable Wait State. An
alertable wait state allows a thread to be preempted or interrupted by an
asynchronous (APC) alert. When an APC is queued, the queued thread is not
directed to call the APC function unless it is in an alertable state. A thread
enters an alertable state when it calls the SleepEx, SignalObjectAndWait,
MsgWaitForMultipleObjectsEx, WaitForMultipleObjectsEx, or WaitForSingleObjectEx
function.
www.bruteratel.com 83
flow to originate from a legitimate region instead of directly from the RX
region. However, the gadgets required for ROP, are found only in a few DLLs of
Windows. In case the required gadget is not found, then the phantom_thread
command falls back to perform hijacking of the thread using a custom technique.
This command uses indirect syscalls where required and does not open a handle to
any process, which makes it the more stealthy in terms of remote injection.
Since this command requires an alertable thread, the operator needs to find a
valid alertable thread that can be hijacked and alerted. C-Sharp process/Windows
Apps cannot be hijacked. Thread states can be enumerated using the threads
command.
Alertable threads can also be created using the suspended_run command which
executes a process in a suspended state, converting the primary thread to be
alertable.
www.bruteratel.com 84
Command: threads
This command returns all the running threads in the system and can filter out
threads that are already in an alertable state. The phantom_thread command when
combined with the threads command can be extremely powerful to hide remote
process injection traces in memory.
Command: psreflect
This command can inject and execute a reflective DLL into a remote process which
loads the CLR DLL to run powershell scripts and Cmdlets without calling
powershell.exe. This command also accepts command-line arguments that can be
supplied to the PowerShell command. Unlike other C2s which load the PowerShell
scripts into memory by hosting it locally and the then using IEX to load it into
memory, badgers load the whole PowerShell script by reading it from local
process memory. The below figure shows execution of a function from a PowerShell
module imported via the psimport command. The psreflect command comes pre-built
with ETW and AMSI patching.
The injection techniques for psreflect can be configured using set malloc and
set threadex.
www.bruteratel.com 85
Command: shinject_ex
This command takes a process ID as the first argument and a position independent
shellcode in either an executable or in a binary blob format as the second
argument. It does not create a new process and only injects the shellcode into
an existing process. The operator needs to have privileges to open a HANDLE of
the target process. The injection methods can be configured using set malloc and
set threadex commands.
Windows Services
Windows services are programs or background processes that run independently of
user interactions, typically in the background of the Windows operating system.
They are designed to provide various functionalities and perform tasks without
requiring a user to be logged in or actively using the computer. Windows
services are an essential part of the Windows operating system architecture and
play a crucial role in system functionality and management.
Command: sccreate
This command can create a local or a remote service via Remote Procedure Call
(RPC). To create a local service, badger needs local administrative privileges
on the current host, and for a remote service creation, it needs an
authenticated network token. The command takes in three arguments: hostname,
service name and path of the service executable.
www.bruteratel.com 86
Command: scdelete
This command deletes a service on a local or a remote host over RPC.
Administrative privileges are required to delete a local service, and an
authenticated network token is required to delete a remote service. It takes in
first argument as a hostname and second argument as the service name.
Command: scdivert
This command changes the service binary path for an existing service on a local
or a remote host, executes the updated service binary path, and then reverts the
path to the original location over RPC. This command takes takes in three
arguments. The first argument is the hostname where the service needs to be
changed, the second argument is the service name, and the third argument is the
path of the new service that will be replaced with the original service path.
Make note that the new service path should be reachable for the target host. The
below figure shows an example where the service binary path for
UserDataAccess_595 service was changed with the badger’s SMB service executable,
and once it was executed, the original path was also restored.
Command: scquery
This command enumerates a local or a remote host and returns a list of installed
services via RPC. It accepts three optional arguments. The primary argument
www.bruteratel.com 87
should be the hostname, secondary argument should be ‘full’ or ‘basic’ to
specify the type of information requested and the third argument should be a
service name. If no arguments are specified, then it returns a list of all
services installed with only basic information on the localhost. The ‘basic’
information does not contain the description or service triggers. If a single
argument (hostname/IP) is specified, then it enumerates the specified host over
RPC (Remote Procedure Calls). If all the three arguments are specified, e.g:
scquery DC01 full wuauserv, then it returns detailed information about that
service including the description and service triggers.
Command: scstart
This command can start an existing service locally or on a target host over RPC.
It takes 2 arguments i.e. the hostname and the service name to start.
Command: scstop
This command can stop an existing service locally or on a target host over RPC.
It takes 2 arguments i.e. the hostname and the service name to stop.
www.bruteratel.com 88
Command: curl
This command performs a http/https request to a given site and url over ssl or
cleartext. It can send a GET request to an HTTP(s) server on a given port and
URI and receive html output in raw format. This command can search and enumerate
internal web applications without the need to start Socks proxy, or to check if
your backup C2 channel is reachable from within the organizational environment.
Command: dns_interval
DNS Over HTTPS requests allow a maximum of 64 bytes per request. If the output
of a command is more than 64 bytes, then this response will be split into
multiple chunks. When sleep is complete and Badger checks in, it encrypts the
available chunks, then sends the chunk without sleeping until all the chunks are
sent. It will then fetch commands from the C2, execute them, store their
response in chunks, and then sleep while encrypting itself and the responses in
the heap. DNS interval, in this case, would be the time interval between various
chunks it needs to send for a single request. During this interval, Badger does
not hide itself. It will just wait a few seconds before sending the next chunk
of data. Once all the chunks are sent, a single request is complete. Badger’s
sleep and DNS interval are different. Badger can’t hide itself when performing
any type of DNS operations because the thread needs to actively read the RX
region or read the RW code within the badger. However, if the badger has zero
www.bruteratel.com 89
threads active, then the Badger will encrypt itself, stack, heap, and everything
related to it. Thus DNS Interval allows to change the frequency at which packets
of DNS for a single request are sent to the server. The dns_interval takes
milliseconds to wait before sending multiple chunks of data. The default DNS
interval is 100ms.
Command: dnscache
The DNS cache is a local storage of DNS records maintained by the operating
system. The DNS cache contains the Resource Records (RR) of the domains you have
previously visited and their IP address translations. When you access a web
page, your computer's OS initiates a DNS lookup for the domain. This command
displays the DNS cache on the current host.
www.bruteratel.com 90
All file downloads are encrypted and use indirect syscalls to read the files
from the disk to avoid any sort of DLP protection. The maximum size of data per
request is also limited by the bandwidth provided by the ISP and the type of
infra the remote host is located in. It's always better to use small chunks of
data such as 512kb or 1MB to lower the attention that you might get during
exfiltration. The get downloads command can list all active downloads in the
badger. The stop_task command can stop an active download with their given task
ID.
Command: icmp_ping
This command sends an ICMP request to a target machine to check if it's
reachable. If it receives a valid acknowledgment, it returns that the host is
alive. Make a note that if the firewall is enabled on the host and ICMP is
disabled, it will return the host is unreachable.
Command: ipstats
This command returns network-related information including names of VPN
adapters, their IP addresses, gateways, and other DNS/Adapter information. This
command was built with Windows API and does not create any process.
www.bruteratel.com 91
Command: lookup
This command performs a network lookup of a given hostname and returns the IP
address of the host.
Command: netshares
The netshares command can be run with or without parameters. It can take two
optional arguments. The first argument is the host to enumerate for shares. If a
host is not provided, it will scan localhost. The second optional argument is
privs. If this argument is provided, then badger will check whether it has
administrative privileges on the remote host. But unlike most share enumeration
tools which try to check privileges on the admin share, this command performs
enumeration on the IPC share. This helps to avoid the usual detection techniques
while checking for privileges on the remote host at the same time. The below
figure shows an unprivileged query to the domain controller (BRDC01) with privs
argument which returns Error 5 which stands for GetLastError Access Denied.
www.bruteratel.com 92
Command: netstat
This command provides statistics about all active connections from computers or
networks the badger’s host is connected to. It returns all TCP/UDP connections
and their listening ports/status and processes on current host.
Command: pivot_smb
This command uses ConnectNamedPipe WinAPI to connect to a named pipe of the SMB
badger. SMB runs on port 445 and they are used to transfer data throughout
Active Directory. SMB Badgers are privilege independent. It means unlike typical
SMB pipes which require authentication, SMB badgers do not require
authentication and any other badger can connect to this named pipe. SMB badgers
named pipe can be configured via C4 Profiler->Profiles->Payload Profiles. Once
an SMB badger is executed it starts to listen on this named pipe. The pivot_smb
command can connect to this named pipe. Upon first connection, the SMB badger
sends the initial connection and authentication request to the pivot badger
(which connects to the SMB named pipe). This badger either forwards it to its
parent badger i.e. other pivots, or if it is an HTTP badger, it appends/prepends
its data and forwards it to the server.
www.bruteratel.com 93
The above example shows the HTTP badger (b-1) creating an administrator token
for the domain (darkvortex.corp), and then using the psexec command to start an
SMB badger on the remote host via RPC (Remote Procedure Call). This command uses
the payload profile configuration (mySmbProfile) and generates a service
executable and starts this service on the remote host. Once the SMB badger
service is executed, it starts to listen on the named pipe (\\.\pipe\
mynamedpipe), and we can connect to this named pipe via the pivot_smb command.
Make note that your pivot badgers need to have the same authentication keys as
your HTTPS listener so that they can authenticate properly after pivoting via
the HTTPS Badger. If the auth key is not the same, then badgers cannot
authenticate.
www.bruteratel.com 94
Now, we execute the TCP badger onto a remote host using psexec, or we can also
execute it any other way. In the current example below, we executed TCP badger
via shinject_ex on the same host which should connect back to our TCP listener
on our IP address 172.16.219.130:10000.
To view all TCP listeners, an operator can select Server->View TCP Listeners or
use the command get tcppivot on the host where the listener was started. An
operator can stop the TCP listener using the stop_task command.
Command: portscan
This command performs a full TCP connect port scan on a given hostname/IP
address and space-separated port numbers or a port range. The scan will be
conducted in the order they are provided in the arguments. This command, by no
means, is a replacement for NMap. It is only to be used to check if a specific
service port is open for lateral movement such as RDP/SMB/DCOM ports and so on.
Mass scans are not recommended using this command it performs a full TCP
connection, unlike the stealth scans from Nmap. The below figure shows a scan
for a hostname. The hostname resolution is performed automatically by the
badger.
www.bruteratel.com 95
A port range can also be provided to this command to perform the scan. The below
figure shows the port range 20-30 alongside other general ports.
Command: ps_ex
This command can enumerate processes on a target server using the Remote Desktop
Services API to query the target server via an authenticated token. If the
target host/server does not have Remote Desktop Services installed, then no
response is received.
www.bruteratel.com 96
Command: psexec
This command is partially similar to that of Microsoft Sysinternal Toolkit’s
psexec. It creates a service on a remote system and starts the service using
Remote Procedure Call (RPC). But unlike Microsoft’s PsExec which uses
CreateProcess API to pipe cmd.exe over SMB, BRc4’s PsExec service contains a
shellcode blob for a payload profile provided during the execution of PsExec.
This payload can either be SMB, DOH, HTTP, or a TCP profile. One of the most
important OpSec considerations during lateral movement is to keep yourself
disguised as a legitimate service. Several PsExec options such as service name,
description, service executable name, and the type of payload to execute on the
remote host are customizable on the go. This can be configured by selecting C4
Profiler->PsExec Config. This allows changing the service name and description
when a PsExec Service is created on the host. To create a service directly from
the profile of a payload, an operator would need administrative privileges on
the target host, access to the admin share and open port 445. Generally, a token
harvested from an administrator’s process or created using the make_token
command with the administrator’s credentials should be enough.
The psexec command accepts two arguments. The first argument is the host/IP
where the service is to be created and the second argument is the payload
configuration name from the Payload Profiler. The above example uses an SMB
profile. Once the above command is executed, the ratel server will create a
payload based on the payload configuration’s name, copy it to the remote host,
create a service, and start the service over RPC. The SMB badger can be
connected using the pivot_smb command.
Command: query_session
This command can enumerate users logged on a current or a target host. It can
extract user information who are logged in via Powershell, rdp, console, etc.
For enumerating remote hosts, a valid token or authentication is required.
www.bruteratel.com 97
Command: routes
This command lists the network routing table for IPv4 addresses which can gather
information on the surrounding hosts. It is similar to the route command in
windows.
Command: rportfwd
Reverse port forwarding is a networking technique that enables a user to access
a service or resource on a remote system from their local machine, even when the
remote system is behind firewalls or NAT (Network Address Translation). It's a
way to establish a connection from a remote machine back to the local machine,
effectively bypassing network restrictions. Reverse port forwarding helps to
bring in your own custom C2 or tooling for moving laterally. This command can
forward a port on Badger’s host directly to the Ratel server, and the Ratel
server will handle the task of forwarding it wherever requested. This example
www.bruteratel.com 98
shows a quick demonstration of reverse port forwarding for Metasploit’s
meterpreter via our badger’s port forward. In this example, we have forwarded
port 8080 on the badger’s host to our Metasploit’s server 192.168.0.150 on port
9443. When meterpreter connects to port 8080 on the badger’s host, it will be
routed to port 9443 on metasploit server. Make note that this metasploit server
should be reachable by the Ratel server, or else the connection would be
dropped.
Command: sharescan
This command takes the hostname separated by newlines in a text file and
enumerates their share. If a host is not reachable, it will return the
respective error for the same. The below example explains it better:
Command: sleep
This command changes the sleep interval of the badger between which the badger
communicates with the Ratel server. An operator can use a jitter value to make
the sleep times dynamic. For example, on entering sleep 30 40, the sleep time
would be 30 second + random value between 30 and (30 % 40). Thus it becomes
difficult for defenders to perform detection on the basis of check-in intervals.
Command: upload
This command takes one argument and can upload files from the Commander’s host
to the target destination in the badger. All file uploads are encrypted and use
indirect syscalls to write files to disk.
Command: socks/socks_stop
A SOCKS (Socket Secure) proxy is a network protocol that facilitates the routing
of network traffic between a client (such as a computer or device) and a server
through an intermediary server known as a proxy server. Unlike HTTP proxies,
www.bruteratel.com 99
which primarily handle web traffic, SOCKS proxies are designed to work with
various types of network traffic, including applications that use protocols
other than HTTP.
The SOCKS proxy protocol operates at the transport layer (Layer 4) of the OSI
model, which means it can handle traffic from a wide range of applications,
including web browsers, email clients, file transfer protocols, and more. When a
client device is configured to use a SOCKS proxy, it establishes a connection to
the proxy server and sends its network requests to the proxy. The proxy server
then forwards these requests to the destination server, and the responses are
relayed back to the client through the proxy. SOCKS5 supports authentication,
TCP, UDP and DNS resolution, whereas SOCKS4A only supports TCP and DNS
resolution.
Both Socks4a and Socks5 are supported in Brute Ratel. The socks client can be
started or stopped with the socks command followed by arguments such as ‘4a’ or
‘5’. If socks5 is used, an operator can also utilize the username and password
functionality of socks for security. Socks can be stopped using the socks_stop
command. A list of active socks server on the listener can be found by selecting
Server->View Active Socks Menu. The below figure shows socks proxy with username
as admin and password as pass123.
To connect to this socks proxy on our Linux host, we will install proxychains4
using the below comand and configure the /etc/proxychains4.conf file. We will
add our host, port, username and password here.
Once this is configured, we can use proxychains to route our traffic via this
host. For example, if you have the credentials of the badger’s host, we can use
the tool remmina to RDP into the badger’s host or any other host reachable by
the badger.
www.bruteratel.com 100
Alternatively if an operator wants to access webservers reachable on the domain
via the badger’s host, then the operator can configure these proxy information
in Firefox or Google Chrome and access the remote hosts from here. Socks can be
used without or without Sleep Zero. Make note that if high sleep value is used,
it might timeout the TCP connections depending on the target application’s TCP
timeout value.
Command: switch_profile
This command takes in a valid profile name saved on the Ratel server and changes
the full network profile of the badger. This command is the command-line version
of Switch Profile here.
Local Enumeration
Command: acl
A Discretionary Access Control List (DACL) is a security mechanism used in
computer operating systems and networks to manage access permissions to
resources such as files, folders, and devices. DACL is a component of
discretionary access control, a security model that allows the owner of a
resource to determine who can access that resource and what actions they can
perform on it. This command enumerates the Discretionary Access Control List for
an object. It can enumerate permissions of a file or folder similar to the
‘cacls.exe’ executable from Windows. The below figure shows the permissions
allowed for each group of users (BUILTIN\Users, TrustedInstaller, System etc.).
This command can enumerate vulnerable folders such as unquoted service path to
escalate badger privileges.
www.bruteratel.com 101
Command: applist
This command enumerates all the installed applications from the registry. The
returned results are the same that one would see in the Control Panel of the
Windows operating system.
Command: cd
This command changes the current working directory of the badger. The command
accepts ‘..’ to navigate one step back from the current directory and ‘../../’
for subsequent previous directories in the directory tree. Remote paths can also
be accessed over SMB provided the user has appropriate permissions/token to
access them. The make_token command can create a token using the credentials of
a user to access a remote network drive.
Command: cp
This command copies a file from one place to another. The target destination
should have the full name of the file that needs to be copied, or else it would
return Error: 123 which stands for GetLastError ERROR_FILE_NOT_FOUND. The cp
command also supports copying over SMB path.
www.bruteratel.com 102
Command: crisis_monitor
During an engagement, there could be several scenarios where a badger might
disconnect from the server. It might be because the badger was flagged due to
some post-exploitation stuff, or maybe the system went to sleep/hibernation or
maybe the battery on the laptop was just low and shutdown. The crisis_monitor
feature monitors this activity for Brute Ratel. This feature constantly checks
for a selected set of events and when that event is executed, it will send a
notification back to the server. The monitored events are:
◦ AC Power: Connected/Disconnected
• System Suspended
• System Resumed
• Session: Logoff
• Session:
◦ User Logon
◦ User Logoff
In all of the above scenarios ranging from power changes to session connection,
disconnection, or user login, the badger will send a notification back to the
server that an event has occurred. This can be extremely helpful in scenarios to
get a quick notification when a member of security team logs in and an operator
might want to pause their post-exploitation stuff in such scenarios which
involve GUI access. Crisis monitor can be stopped using the stop_task command.
www.bruteratel.com 103
Command: drivers
This command returns a list of drivers loaded on the host alongside their
metadata which can be useful to identify EDR drivers on the host.
Command: dumpclip
The dumpclip command extracts the clipboard text information stored in memory
and returns it to the badger’s console. This can monitor a user’s clipboard
activity such as extracting any copied credentials in memory.
www.bruteratel.com 104
Command: exit_process
This command exits the process in which the badger is residing. The process is
killed.
Command: exit_thread
This command exits the thread in which the badger is residing. The process stays
active.
Command: fileinfo
This command reads the size, creation time, last access time, last write time,
change time, company name, and the description of the file and prints it to the
screen.
Command: idletime
This command returns the inactive time of the current user.
Command: keylogger
This command captures the user’s keystrokes for all windows. To view the
captured output, the operator will have to stop the keylogger using the
stop_task command. The output is stored in memory and not returned to the user
till the task is stopped.
www.bruteratel.com 105
Command: kill
This command takes a process ID as an argument and terminates it. The operator
should have privileges to open a process handle in order to successfully kill
the process.
Command: list_modules
This command lists all the DLLs loaded in the current process or a target
process. It takes a PID as an optional argument to list the DLLs loaded in a
target process. This command can be useful to enumerate Dlls loaded by security
solutions or to check if Clr.dll is loaded in the process for dotnet reflection.
Command: local_sessions
This command can enumerate active sessions on the badger’s host. It returns the
type of logon, the status, the session ID, and the username of the logged-in
user. This command when combined with crisis_monitor and grab_token can be
really powerful to get a notification as soon as a user logs in, validate the
www.bruteratel.com 106
user, and steal the token to further move laterally or execute some command from
the stolen token.
Command: lockws
This command activates lockscreen on the badger’s host.
Command: ls
This command can list the files and folders either in the current directory or
over SMB. Files that are inaccessible or cannot be opened are listed below the
main table of the ls command.
This command when run on a filepath, can provide information on whether a file
exists or not. The below figure shows a quick example of the behavior of this
command on a file. The first path (C:\windows\system32\etc\drivers\hosts) is
invalid and it returns GetLastError: 3. The second path is valid, but it is not
a directory. Thus it returns Error reading file. This means the path is valid,
but it is not a directory.
www.bruteratel.com 107
This command can also enumerate named pipes on the host, which can be useful to
build SMB payloads for pivoting.
Command: lsdr
This command lists all mounted drives in the current host. This command does not
show the network path. To view network mounts, use the netshares command.
Command: mkdir/rmdir
This command creates a new directory. Alternatively, The rmdir command can
remove/delete a directory from the host.
Command: mv
This command moves a file from one location to another. The target destination
should have a full name of the file that needs to be copied, else it would
return E: 123 which stands for GetLastError ERROR_FILE_NOT_FOUND.
www.bruteratel.com 108
Command: preview
This command reads the first 8192 bytes of a file from the disk and displays the
content on the screen. It uses indirect syscalls to read the file from the disk
to evade generic DLP detections.
Command: ps
This command lists all the running processes on the badger’s host. It returns
the parent process Id, process Id, domain/user, architecture, thread count, and
the process path. If the badger does not have privileges to read the target
process, then the process architecture and Domain\User name would show up as NA.
Command: psgrep
This command takes an argument as a process name, and searches the list of
running processes to check if the process exists. If more than one process is
found, it returns all of them.
www.bruteratel.com 109
Command: pwd
This command returns the current working directory for the badger.
Command: record_screen
This command records the screen of the target host and returns an AVI file in
the downloads section. It can take arguments as quality (low/medium/high) and
the number of minutes to record the screen on the host. The recording can also
be stopped before the timer completes by using the stop_task command. The size
of the AVI file heavily depends on the resolution of the target host’s screen
and the quality requested to be captured.
Command: reg
This command uses the Windows Registry APIs to query different hives and keys of
a Windows registry. Currently, it only supports querying the registry and does
www.bruteratel.com 110
not support adding keys or DWORD values. A registry key can be queried as
follows:
To enumerate the key entries, an operator can specify the full path of the main
registry.
Command: rm
This command can delete files accessible by the badger. It also takes an
optional argument ‘rf’ which overwrites the file with garbage data multiple
times, and then zeroes it out before deletion. This performs secure deletion of
files making it harder to recover files during forensics.
Command: run
This command creates a new process and returns the output from that process. It
supports PPID spoofing, Command-line Argument spoofing, and Dll blocking
(mitigation policies).
www.bruteratel.com 111
Command: schtquery
Scheduled Tasks on Windows refer to a feature that allows users to automate the
execution of specific programs, scripts, or tasks at predefined intervals or
based on specific events. These tasks are configured to run without requiring
manual intervention and can help streamline various system management and
maintenance activities. Scheduled Tasks are managed through the Task Scheduler
utility in Windows operating systems. The schtquery command can perform a
detailed enumeration of scheduled tasks on a current or a target host. The
optional argument ‘full’ enumerates and returns the XML information of the
scheduled task. This commands supports windows access tokens.
www.bruteratel.com 112
Command: screenshot
This command takes a screenshot of the current host and streams it automatically
to the Ratel server without dropping it to disk. This command takes a screenshot
of all monitors connected to the host. The screenshot can be viewed by selecting
it in the Downloads tab and viewing it.
Command: shellspawn
This command uses the ShellExecuteExA WinAPI to execute commands. It accepts
three arguments. The first one can be ‘open’ or ‘runas’. The ‘open’ command uses
the default configured application to open a file (second argument) on the host.
www.bruteratel.com 113
The ‘runas’ argument can execute a file as a privileged user, but it will prompt
User Account Control (UAC) dialog box to the user i.e. only if the current
badger is running as an un-privileged user. The next arguments could be extra
command-line arguments for the application.
Command: stop_task
Most badger commands can be stopped at any minute using the stop_task command.
To check which commands support this, use the help <command> command and check
it’s supported command information.
Command: sysinfo
This command returns basic system and hardware information.
Command: timeloop
This command can run a Badger’s command for an x number of times, every y number
of seconds on the host. For example, let’s say a jump server was compromised and
high integrity privileges were gained, but there is no user logged in on the
host. Now the shadowcloak command can dump credentials, but it’s useless unless
a user logs in and caches their password. So, in this case, an operator can run
the timeloop command to extract the memory every x number of times with a given
interval. The timeloop command accepts three or more arguments. The first
argument is the number of times you want to run the command, the second argument
is the interval under which you want to run the command and the third argument
is the actual command to run which can have its own set of arguments. The below
command executes the screenshot command every 3 seconds for a total of 5 times.
www.bruteratel.com 114
The timeloop command can be run during high sleep intervals because it does not
need to connect to the server to run the command. You can assign a timeloop
command to the Badger, let it check in, and then put the badger to sleep for a
long time. While the Badger is sleeping, it will run the timeloop command as per
the interval and counter provided. It will cache the output to memory without
connecting to the server, and then sleep in an encrypted Read-Write region in
memory. Once it checks in, post your sleep interval, the whole output will be
returned back to the server.
Command: uptime
This command returns the active time of the host since it was last shutdown. It
returns the number of minutes that have elapsed since the system was started.
Command: userinfo
This command displays the current user name, SID, privileges and groups. It is
similar to the whoami.exe /all command, but without process creation.
www.bruteratel.com 115
Command: windowlist
This command displays all hidden and visible windows for all applications
currently open on the host.
www.bruteratel.com 116
Active Directory Enumeration
Command: dcenum
This command queries the Active Directory Domain Controller and returns basic
information for all the domain controllers in the current domain.
Command: dcsync
DCSync is a technique used in Windows Active Directory environments to retrieve
and replicate Active Directory (AD) account credentials, including password
hashes, from a Domain Controller (DC) to an attacker-controlled system. This
technique is often employed by attackers to escalate privileges and gain
unauthorized access to sensitive data within an organization's network. DCSync
takes advantage of the way domain controllers replicate information among each
other in an AD domain. It uses the Active Directory Replication technique to
request NTLM hashes for the specified users from a give domain.
www.bruteratel.com 117
This command is a standalone command separate from the mimikatz module. It runs
inline and can be used with an impersonated token created with the make_token or
impersonate command. This command takes an optional username and domain name as
argument. If no argument is provided, then it will request NTLM hashes for all
the users in the current domain. This command does not inject anything and all
the DC replication requests are performed from the badger’s process itself.
Command: net
This command uses NetAPI to list user and group information on the local host
and Active Directory. This command is not to be confused with the net.exe
executable which is a process instead of a windows API. This command accepts
multiple parameters. Make note of the difference between the argument ‘users’
and ‘user’. The ‘users’ argument will enumerate all users, however, if the
‘user’ argument is used, then a third argument – username will be required, with
an optional fourth argument to specify which user to enumerate and on which
host/domain.
www.bruteratel.com 118
Same applies for the ‘groups’ and the ‘group’ command.
Command: passpol
This command enumerates the password policy of a current or a target host. The
optional argument takes in a target hostname. Any domain user can use this
against a host in a domain without requiring any special privilege.
www.bruteratel.com 119
Command: sentinel
Ldap Sentinel can run customized or pre-built LDAP queries against an Active
Directory Domain Controller. This command can be used from the GUI (Right Click
Badger->Arsenal->LDAP Sentinel), or from the terminal using the sentinel
command. The sleep and jitter interval for this command can be configured using
the set sentinel_sleep command. Sentinel takes in two minimal arguments, and
more optional arguments as LDAP filters. The first argument can be ‘domain’,
’forest’ as strings, or the actual domain name to query. The second argument has
to be a valid LDAP query. The optional arguments after these are LDAP filters to
view only selected attributes. The below example shows entering a query in the
sentinel commandline interface which does not take the first argument as it can
be filtered using a dropdown next to it.
www.bruteratel.com 120
Command: set/get sentinel_sleep
This command accepts sleep and jitter values for the LDAP Sentinel’s sentinel
command. Using this, operators can provide an interval between every single LDAP
request to the Domain Controller sent via LDAP Sentinel. To fetch the active
configuration, use the get sentinel_sleep command.
Credential Harvesting
Command: make_token/revtoken
In the Windows operating system, a security token is a data structure that
contains information about a user or process's identity and privileges. Token
privileges are a part of this security token and define the specific rights and
actions that a user or process is allowed to perform on the system. These
privileges determine the scope of actions that can be taken, such as modifying
system settings, accessing sensitive resources, or performing administrative
tasks. This token can access a specific host, data, or service within an Active
Directory or Azure cloud environment. The make_token command can create a
security token to impersonate a user. Make note that this command does not
escalate local privileges or bypass UAC. It can only be used to access current
host objects for local tokens, and network shares/RPC calls for remote hosts
using network tokens. This command takes four arguments: type of token, host
FQDN, username and password. The below figure shows an example of pivoting using
SMB badger (RPC calls) using the network token. The (SMB) value in the psexec
command below is the name of the SMB profile added to the server. More
information on this command can be found here.
www.bruteratel.com 121
The make_token command also supports creating local tokens instead of just
network tokens. Local tokens allow you to access the directories of other users
within the same host which is not possible with network tokens. To revert a
token, simply use the revtoken command to revert the token back to the original
user. This command can also be used from the Creds tab in Commander.
Command: addpriv
This command can add a privilege to the badger. However, the privileges should
be available within the current process. For eg.: a process with admin
privileges will have SeDebugPrivilege/SeLoadDriverPrivilege, but they are not
enabled by default. The below example shows the privilege for
SeLoadDriverPrivilege acquired by the badger. A detailed list of privileges that
can be enabled can be found here.
Command: get_system
This command duplicates a token from a process running with system privileges
and assigns that token to the current thread of the badger process.
www.bruteratel.com 122
Command: grab_token
This command can extract tokens from processes by opening their handle and
storing them within the badger. An operator can hot-swap tokens without
sacrificing the existing token. Make note that the badger will still need local
administrative privileges on the host to steal the token as it requires opening
a process handle to the remote process. This permission is only accessible to
the process owner, the parent process, or a local administrator on the host. The
extracted token is stored in the Token Vault which can be accessed using the
command get token_vault. To impersonate a token, use the impersonate command
with the token ID.
www.bruteratel.com 123
Command: get token_vault
This command returns harvested tokens stored in the token vault. These tokens
can be used via the impersonate command to impersonate the user from the token.
Command: vault_remove
This command removes a token using the token ID from the token vault.
www.bruteratel.com 124
Command: clear vault
This command clears all stored tokens present in the token vault.
Command: impersonate
This command works alongside the grab_token and the get token_vault command.
Harvested tokens stored in the vault can be impersonated with this command. More
information on this can be found here.
Command: kerberoast
Kerberos tickets are a fundamental component of the Kerberos authentication
protocol, which is widely used for authenticating users and services in
networked environments. Kerberos is commonly employed in Windows Active
Directory domains and other networked systems to provide secure authentication.
A Kerberos ticket is a data structure that represents the authentication and
authorization information for a user or service. It consists of two main parts:
the Ticket Granting Ticket (TGT) and the Service Ticket.
This command will perform an ASREQ to fetch a kerberos service ticket for a
valid SPN and return the KRB5 encoded ticket. This ticket can be cracked using
hashcat. An operator can specify any number of SPNs to this command and it will
fetch the tickets recursively for all of them. The SPN name has to be in the
format of name/host.
www.bruteratel.com 125
This ticket can be decoded and converted to the Hashcat format using krb5decoder
from the BRc4 package.
Command: memdump
This command can dump the memory of any process filelessly. It uses various
indirect syscalls and reads the memory of the remote process. Instead of the
www.bruteratel.com 126
dropping the memory to disk, the read buffer is routed via hooks to a badger
handled buffer, which is encrypted and exfiltrated over network. The status of
the download file can be viewed using the get downloads command.
This command uses the same technique as the shadowcloak command. Make note that
the badger will need proper privileges to open a handle to the target process to
read its memory.
Command: mimikatz
This command is a reflective DLL version of Benjamin Delphi’s mimikatz. It
requires a privileged process (high integrity) to run its commands. Badgers can
load mimikatz’s reflective DLL module to perform all of the mimikatz commands in
memory. The below example shows the password-dumping technique.
Make note that if you want to run subcommands of a module within mimikatz, each
submodule has to be in double quotes. The mimikatz module is an exact replica of
www.bruteratel.com 127
the mimikatz from Benjamin Delphi’s repository and is updated every 3 months. An
example of subcommand would be as follows: mimikatz “lsadump::dcsync
/domain:bruteratel.corp /user:vendetta”.
Command: phish_creds
This command can capture credentials using a phishing technique. It takes one
argument as the name of the process that it would impersonate and returns a
dialog box to the user to enter their credentials.
Once the command is executed it requests the user to enter their username and
password.
Command: pth
Pass-The-Hash technique takes user credentials in the form of an NTLM hash,
creates a new process with an empty username and password, and replaces the
password with the hash supplied by the operator. Once this is successful, the
process is resumed, its token is extracted and impersonated, and the process is
then killed. This allows the badger to use the impersonated tokens from the hash
for lateral movement and further post-exploitation. Badger’s pth command allows
the operator to either spawn a new process from an NTLM hash or simply
impersonate a token from an NTLM hash. Make note that even to impersonate the
token, a process will be created and then killed. This command is an improvised
version of Mimikatz’s PTH functionality with more built-in OpSec to avoid
various EDR detections.
www.bruteratel.com 128
Command: runas
This command creates a process for a user using cleartext credentials. Due to
the nature of this windows API, it’s not possible to fetch the output of the
command, since the security token for the created child process with different
credentials will be different from the security token of its parent process. The
process path should not have a space, or else the badger won’t be able to parse
the command line arguments. Make note that the process path should also be
accessible by the user whose credentials are being used.
Command: samdump
SAM stands for the Security Account Manager which manages all the user accounts
and their passwords in Windows and starts up on boot. These passwords are hashed
and then stored in SAM. LSA (Local Security Authority) is responsible for
verifying user login by matching the password hashes with the database
maintained in SAM. By default, Windows does not provide any functionality to
extract the hashes of the local user while it is booted. However, these
credentials can be extracted by reading them from the SAM Hive and memory. The
samdump command can dump the NTLM and LM hash of all local users in the current
host. If this command is run on a Domain Controller, then it will dump the
hashes for all the users including the password history. This command first
impersonates SYSTEM/NT AUTHORITY, reads the hashes, and then reverts back to the
original token before dumping the credentials.
www.bruteratel.com 129
Command: shadowcloak
Shadowcloak is a memory dump technique that uses indirect syscalls to read the
memory of lsass.exe and downloads the memory buffer directly to the Ratel Server
instead of touching the disk. This command is similar to the memdump command,
but instead, it auto-detects lsass.exe and downloads its memory dump which can
be used alongside mimikatz offline.
Command: system_exec
This command is similar to the get_system command which duplicates a token from
a system process and assigns that token to the current badger process. Once the
token is impersonated, it will execute the provided process by the operator, and
then revert the token.
www.bruteratel.com 130
WQL to manage different components across a network over RPC. This command can
query the WMI COM Server locally or remotely in memory. Usually, WMI is executed
via PowerShell or wmic.exe, but Microsoft provides COM DLLs which can interact
with COM objects. Badger provides set wmiconfig, get wmiconfig and clear
wmiconfig to configure the WMI namespace, domain, username and password to
interact with the remote system. The below figure shows WMI configured for the
DC (VORTEXDC) for namespace \\root\cimv2 alongside the domain admin credentials
to query operating system information. Similar if wmiexec is executed, it would
execute the provided process argument on the remote host.
Once the credentials are configured, all queries performed using wmiquery or
wmiexec will use this configuration. The clear wmiconfig command resets this
configuration.
Command Configurations
Command: set
The ‘set’ command can configure various commands as can be seen in the figure
below.
The optional arguments show the configuration parameters that can be configured.
Each sub-commands’s supported_cmd option shows the commands that are affected
after configuring this command. Use the help set <command> to get the
information on supported_cmd.
Note: Some commands belonging to other sections, eg.: ‘set malloc’ are not
included in this section.
www.bruteratel.com 131
Sub-command: set killdate
This command will configure a badger to exit on a given kill date irrespective
of whether the badger is connected to the server or not. It accepts a date in
the RFC822 format e.g.: 09 Sep 23 22:55 EST.
Command: get
The ‘get’ command can fetch the configurations of various commands as can be
seen in the figure below.
The optional arguments show the configuration parameters that can be retrieved.
www.bruteratel.com 132
Commander Commands
Command: cls
This command clears the output of badger’s command in the badger’s terminal
temporarily. Make note that if the terminal window is closed and reopened, then
the data will reappear because it is not erased from the badger’s logs on the
server.
Command: clearq
Badgers are asynchronous in nature. Once a badger completes its sleep cycle, it
will connect to the server to request all the tasks in the queue, download the
tasks, run the requested tasks, and return a response the next time it checks
in. When a badger is sleeping, the commands are queued on the server. This
command clears the queue of commands stored on the server.
Command: help
This command takes one or more arguments to return descriptive information about
a command for the badger.
Command: note
This command adds a note to a badger which is displayed in the badger’s tab.
Command: title
The title command is used to rename the badger’s console.
This is only temporary till the badger’s console is active. If you close and
start the console, it will revert back to the original title i.e. to the
‘process_id@badger_id’ format.
www.bruteratel.com 133
Fallback profiles in payload configurations allow for multiple malleable profiles that enable autonomous switching if one or more profiles or domains become blocked or unusable. Each fallback profile can contain another subset of profiles, providing a hierarchy of profiles for dynamic evasion strategies. This means that if an operator's primary domain gets detected and blocked, the fallback mechanism automatically shifts to another configured profile, reducing the risk of loss of connection or detection by adversaries . This autonomous switching is crucial during operations to maintain persistence and avoid detection without manual intervention . The fallback mechanism includes a "fallback counter" that specifies the number of attempts to connect to the primary profile before switching to a fallback . Profile switching occurs seamlessly, using an encrypted fallback profile metadata, adding another layer of security and flexibility for red team activities .
The 'psgrep' command is effective in identifying and verifying the existence of running processes by taking a process name as an argument and checking the list of active processes. It can return all instances if multiple matches are found . In terms of network security, psgrep could potentially be used by attackers to validate the presence of certain security or monitoring processes on a target system, aiding in circumventing defenses. Moreover, by confirming active processes, an attacker can make more informed decisions regarding subsequent actions, potentially escalating privileges or moving laterally within the network .
The 'timeloop' command is advantageous for executing commands repeatedly at specified intervals, especially useful when operators have high privileges but no active user sessions on the host. This capability allows for operations such as continuously extracting memory dumps or taking repeated screenshots until a user logs in and cached credentials become available for actions like credential dumping. Additionally, it can be deployed during high sleep intervals to minimize server connections, executing commands and caching results locally until the Badger checks back in, thus enhancing stealth and operational efficiency . Furthermore, the command is executed independently of server connectivity, providing a stealthy approach to command execution without needing constant communication with the command and control server .
The 'windowlist' command plays a crucial role in monitoring and controlling application windows by displaying all hidden and visible windows for applications currently open on a host . This functionality can be particularly useful in security auditing as it helps in identifying unauthorized or malicious applications running on a system, providing a clearer view of potential threats . By listing all open windows, security analysts can cross-reference known applications with those that are running, allowing for better detection of anomalies or suspicious activity . Furthermore, the capability to view both hidden and visible windows ensures comprehensive monitoring, crucial for maintaining system security and integrity .
The role of 'die_offline' in a Payload JSON profile is to determine whether a payload should terminate itself if internet connectivity is not available during its initial connection. When set to 'true', the payload will kill itself if it cannot connect to the internet, which can help maintain operational security by preventing the execution of the payload in environments without internet connectivity .
Using the 'record_screen' command in cyber operations involves recording the screen of a target host and returning the recording in an AVI file format. Operators can specify the quality of the recording (low, medium, or high) and the duration of the recording in minutes. The task can be terminated early using the stop_task command. The file size depends on the screen resolution and quality set. This command can impact an operation's stealth because it captures visible activity on a target's screen, which might be crucial for intelligence gathering without alerting the user. However, its use could potentially be detected due to the file size and the changes in network activity or system resources.
The 'schtquery' command supports system maintenance through automation by allowing users to automate the execution of specific programs, scripts, or tasks at predefined intervals or based on specific events. These tasks run without requiring manual intervention, streamlining system management and maintenance activities. Key features include the ability to perform detailed enumeration of scheduled tasks on a current or target host and returning XML information of the scheduled tasks when the 'full' option is used. It also supports Windows access tokens for secure task handling .
Enabling debug logs for DOH will slow down the badger's response and request time .
Named pipes in SMB payloads allow connections over Named Pipe protocols, facilitating communication between badgers without additional permissions. This bypasses traditional TCP reverse connections, enhancing stealth and making unauthorized connections less detectable .