njRAT, also known as Bladabindi, is a Remote Access Trojan (RAT) which allows the adversary to control the end-user’s computer. It was first found in June 2013 with some variants traced to November 2012. It was made by a hacking organization from different countries called M38dHhM and was often used against targets in the Middle East.
Initial Recon & Metadata
First, I check the executable details using file command (ex. 1)

We can see that it is PE32 (Windows) executable and a .NET assembly so we can later decompile it back into C# code.
The analysis will be performed on a sample with the following MD5 hash (8d84f5becf22d3bceb322273fa2ac133) which we can confirm using md5sum command (ex. 2).

I also looked up the hash on VirusTotal (ex. 3). It is pretty widely recognized by most of the vendors already.

Next step is running strings utility so we are able to scan through the binary file and extract sequences of ASCII characters that meet certain threshold of character length. For easier analysis I redirected the output to a text file.
strings njRAT_sample.exe > njRAT_strings.txt
First thing that I noticed is „System.Net.Sockets” which is a namespace in the .NET API (ex. 4)

We can also see TcpClient class that is part of the namespace. There are also other similar methods/classess e.g.
That’s a hint that the malware connects to some entity which is probably just a C2 server.
The following API elements indicate typical RAT behaviour:
1. Registry Manipulation, likely used for persistance eg. Disabling security or implementing run on startup.
2. Keylogging Capabilities
3. Screen Capture / Webcam spying
4. File and Data Exfiltration
5. Compression and Obfuscation
There are a lot more of these but I think its time to dive deeper into the static analysis. This is a .NET assembly so I will use ILSpy tool on linux and dnSpy on Windows to decompile the sample.
Configuration, flags, dynamic runtime variables

Right away it can be seen that obfuscation in case of this njRAT is not the priority. The configuration is mainly hardcoded. Here is some information that can be extracted. I will also mention a few variables that are used in the flow and their function.
CONFIGURATION
Note: The IP address has not been altered, and interacting with it may have unintended consequences.
Name | Default Value | Purpose |
HH | 43.255.241.232 | This is the actual C2 address that is used for communication |
P | 5555 | Port used for communication with the C2 server |
EXE | Notepad.exe | Default value for a name – it is re-evaluated later in the flow based on the actual file name |
sf | Software\\Microsoft\\Windows\\CurrentVersion\\Run | Persistence mechanism – it is used to add the malware to autorun procedure |
RG | f7c5ecd48555dff5f89453188d5fb470 | This value is a unique identifier of the malware used for mutex check (to verify if it is already running) and persistence mechanism (to add it to registry) |
VN | V2FyWnYx | A base64 encoded string – translates to „WarZv1”. Likely a botnet name |
VR | im523 | Version |
Y | |’|’| | Separator |
FLAGS
Flag | Default Value | Purpose |
task | False | Self-protection mechanism (e.g., process monitoring) |
usb | False | USB spreading |
anti2 | False | Security tool termination (taskkill /F /IM …) |
HD | True | Hides the executable |
Idr | True | Ensures it runs from the correct directory (relocates if necessary). |
IsF | True | Startup folder persistence is enabled. |
Isu | True | Registry persistence is enabled. |
BD | True | controls whether the malware enables or disables termination protection during system shutdown/logoff. |
udp | – | Used to flag if udp attack is currently performed |
Cn | False | Flags C2 connection status |
DYNAMIC RUNTIME VARIABLES
Name | Default Value | Purpose |
anti | Exsample.exe | This value is used for evasion – can be set to any particular value to kill security tools |
TIP | – | Target IP used in DoS attacks |
Tport | – | Target port |
delay | – | delay used for rate limiting the udp packets in DoS attacks |
C | – | Part of System.Net.Sockets. TcpClient class used to define the host |
DR | „TEMP” | default value for executable directory location |
Establishing C2 communication
Establishing connection to the C2 is done through connect() function. Lets go through it step-by-step.
Step 1: Checking the existing status

The function marks the malware as disconnected initially by setting OK.Cn flag to False. It then waits 2 seconds before attempting to reconnect. (ex. 6)
In the first try block it checks if OK.C – (TcpClient) is active, if yes it cleans it up before making a new connection.
Step 2: Establishing TCP connection
Below the TcpClient object is created. It also configures buffer sizes (200KB) and timeouts (10 seconds) (ex. 7).

This code (ex. 8) establishes a connection to the C2 server using the IP address stored in OK.HH and the port stored in OK.P. The NewLateBinding.LateCall method is a VB.NET dynamic invocation technique, allowing the malware to call the Connect method at runtime without direct binding.

Step 3: Sending initial data
The Ok.Cn flag is set to true which means there is an existing connection and OK.Send sends initial information about the target that are gathered by OK.Inf function. (ex. 9)

Last thing before returning is gathering and sending data about the flags. These flags indicate what has been done and what is the configuration on this particular malware. Flags are predefined and hardcoded so the malware will know which actions to take, even without initial C2 connection. (ex. 10)

The above data includes:
- Hostname and Port (OK.H, OK,P)
- Directory information (OK.DR)
- Executable name (OK.EXE)
- All the flags that show the malware initial actions and configuration
All of the information is encoded by OK.ENB and sent to the C2 server.
Sending data to C2
The data is being sent via Sendb() function (ex. 11).

Not to overanalyse I’ll focus on the core of this function (ex. 12). First the data is formatted. MemoryStream is used as a temporary buffer to hold length and the data itself. OK.SB encodes the data to UTF-8.

The actual data transmission occurs using the method below (ex. 13).

OK.C is the TcpClient that must be already connected to the C2 server. OK.C.Client.Send will result in sending the data to the connected entity. memoryStream.ToArray() is the data itself in a byte array format.
How does njRAT listen for commands?
Listening for C2 network traffic is a core functionality of any RAT. How does njRAT achieve that? Lets look at the RC() function (ex. 14).

Everything is running in for(;;) loop indefinetely. flag is the result of existing TcpClient connection. If it isn’t true, the RC funtion won’t do anything.
num = -1L; is for tracking expected lengths of incoming data
num2 = counter to ensure the CPU is not consuming too much resources. It is iterated every loop. We can see that every 10 loops it delays the next round of looping (ex. 15).

Next, RC ensures that there is data to read with .Available, if not – it calls Poll() to wait for it (ex. 16).

Below, the data is received and processed byte by byte using the switch statement (ex. 17).

Code | Byte received – meaning | Action Taken |
-1 | End of stream – connection closed | Breaks loop, likely reconnects |
0 | Null byte (\0) – End of command length | Converts text to num (expected byte count) |
default | Any other byte – Part of the command length string | Appends to text |
Interestingly, the data format for both sending and receiving follows the same structure:
[Message Length] + „\0” + [Exfiltrated Data] – in case of data leaving the host
[Message Length] + „\0” + [Command] – in case of commands for the host
Now that the length is known, the whole command can be received. It is done by allocating OK.b byte array of the earlier computed length. OK.C.Client.Receive receives the data and writes it to OK.MeM (ex. 18)

Command received! Next step is to pass it for processing. njRAT does it asynchronously by calling OK.im function in a new thread (ex. 19). After that it clears its memory and awaits new commands.

Next thing in the flow is for the command to be parsed by the command handler function – let’s take a look at how it’s done.
Command Handler: Data Exfiltration, Remote Code Execution, and More
The decision making part of this njRAT sample is surely done by the Ind() function – it is called by OK.im which like I showed, receives the data from the listener – RC () function.
First step is to take the data and get it ready for comparing (ex. 20). „array” is the buffer which is filled by spliting the data ’Strings.Split’, encoding it to UTF-8 ’OK.BS’ and using delimiter ’OK.Y’ which is just „|’|’|”
text = array [0] – this is equal to the first element in the array -> the command!

Due to the fact that there is a lot of available features I will be classifying them. Also there is too much code to show the logic behind every single one of these functions but I will try to show the most relevant ones.
1. System Control and Persistence
Most of these commands use Interaction.Shell API call to run the command eg. Shutdowncomputer (ex. 21)

Command | Functionality |
shutdowncomputer | Shuts down the infected system using „shutdown -s -t 00” |
restartcomputer | Restarts the infected system using „shutdown -r -t 00” |
logoff | Logs out the current user using „shutdown -l -t 00” |
un | Uninstalls the malware (likely against forensic analysis) |
up | Updates the malware by downloading a new binary and restarting |
prof | Reads/Writes registry values based on attacker-supplied parameters |
IEhome | Modifies the IE homepage |
DisableCMD / EnableCMD | Alters registry to disable or enable Command Prompt |
DisableRegistry / EnableRegistry | Disables or enables registry editor |
DisableRestore / EnableRestore | Disables or enables system restore functionality |
DisableTaskManager / EnableTaskManager | Disables or enables task manager |
The „un” command is worth a little more explanation. It calls a function that:





2. Keylogging and Data Exfiltration
Command | Functionality |
kl | Starts the keylogger, capturing keystrokes |
pas | Downloads and runs a password stealer (Pass.exe) from Dropbox |
CAP | Takes a screenshot, compresses it and sends to the C2 server |
3. Network Attacks
Command | Functionality |
udp | Performs UDP flood DoS attack to specified target IP and port |
udpstp | Stops the attack |
4. C2 Communication and Remote Execution
Command | Functionality |
pingstop | Kills all active pings (taskkill /F /IM PING.EXE) |
OpenSite | Opens a specified website |
reconnect | Forces the malware to reconnect to the C2 server |
ll | Terminates the C2 connection setting OK.Cn flag to false |
nwpr | Runs arbitrary process |
rn | Downloads and executes any arbitrary files |
5. Disruption, Chaos, Trolling
Command | Functionality |
DisableKM/EnableKM | Blocks or enables input devices eg. mouse, keyboard |
TurnOffMonitor / TurnOnMonitor | Turns the monitor off/on |
NormalMouse / ReverseMouse | Swaps mouse buttons |
CursorHide / CursorShow | Hides or shows cursor |
sendmusicplay | Plays audio |
OpenCD / CloseCD | Open/Closed CD drive |
piano | Plays a beep sound for 300 ms |
BepX | Plays a beep sound with specified frequency and duration |
peech | Triggers Windows Text-to-Speech |
ErorrMsg (yes, with the typo) | Displays different kind of error msg boxes with specified flags |
While these commands are hardcoded, the adversary’s capabilities extend far beyond them. With remote code execution and the un command, which allows for malware updates, the attacker maintains near-unlimited flexibility to modify, expand, or replace functionality as needed.
Now let’s take a look on one of the functionalities – keylogger.
Keylogger functionality analysis
WRK () – keylogger function that is triggered as one of the first data exfiltration functions. Here is a quick overview of how it works.

do While provides continuous execution, it iterates through 0-255 with the help of num2 variable.
If statement checks for pressed key with the value of num2 [GetAsyncKeyState] sets MSB to 1 if a key is pressed]. The whole statement will not be true if the CTRL key is down – probably to avoid logging CTRL+KEY shortcuts.
The key in it’s value format is assigned to „Keys k” which then is processed by Fix() function (ex. 28).

Fix() seems to be a way of checking if the key pressed is one of the special characters that it would like to ignore/alter for logging purpose.
Last two steps of Fix() are to check if any of the characters suppose to be uppercased and converting it to unicode before returning.
Coming back to the WRK() function briefly just to jump to the AV() function (ex. 28). We can see that Logs is being populated with both AV results as well as with the „text” itself. The AV() function plays a crucial role in tracking user activity by identifying the application in which the victim is typing, extracting relevant metadata for logging.

AV gathers information using API and logs it in a format that might be expressed by an example like: 24/01/19 chrome Facebook – Google Chrome
Lastly WRK saves all of the collected and formatted data to „Logs” for future use.

I think that’s enough of source code analysis. To discover a little more about the C2 or maybe the creator I decided to do some OSINT
OSINT FINDINGS
Censys shows that the IP is static, provided by „Best IDC” with location in Bangkok, Thailand (ex. 29). Most likely this is a rented VPS server running Windows OS.

There are also multiple services open including FTP, HTTP, WINRM.
The FTP is in fact live but it doesn’t accept anonymous login (ex. 30).

There is an HTTP site being hosted under the malicious IP

The rough translation is:
Top up, change password (Support)
Contact admin
Download (Download)
FullClient
Both „contact admin” and „Fanpage” lead to a facebook page called „AmazonZ Revolution” (ex. 32) with some gaming content. Download points to google drive hosting a compressed archive called „AmazonZ Full.rar”

Surprisingly the IP is not flagged heavily as malicious on VirusTotal (ex. 33).

In the ThreatFox database the IP is correctly identified with botnet_cc threat type with 100% confidence (ex. 34).

There isn’t much more noteworthy information to cover here, aside from a deeper analysis of the zipped package from Google Drive – which is a topic for another post. For now, let’s move on to the summary.
Summary & MITRE ATT&CK Mapping
Sample Overview
Key findings
Keylogging and Data Exfiltration
Evasion and Persistence
Remote Command Execution
System Disruption
DoS Capabilities
MITRE ATT&CK
Tactic | Technique |
Execution | T1059 – Command and Scripting Interpreter |
Persistence | T1547 – Boot or Logon Autostart Execution |
Privilege Escalation | T1548 – Abuse Elevation Control Mechanism |
Credential Access | T1056 – Keylogging |
Discovery | T1082 – System Information Discovery |
Lateral Movement | T1091 – Replication through removable media |
Collection | T1113 – Screen Capture |
Command & Control | T1071 – Application Layer Protocols |
Exfiltration | T1041 – Exfiltration Over C2 Channel |
Impact | T1498 – Network DoS |
Defense Evasion | T1070 – Indicator Removal, T1562 – Disable Security Tools |
Final Thoughts
This njRAT sample demonstrates classic remote administration and botnet capabilities, prioritizing data theft, persistence, and system disruption. While it lacks advanced obfuscation techniques seen in more sophisticated malware, it remains a serious threat – particularly when deployed against unprotected systems. Its ability to evade detection, disable security tools, and establish long-term access makes it a viable tool for cybercriminals targeting exposed or poorly secured environments.