typeanalysisfamilyunclassified-dotnet-bitmap-stego-loaderconfidencelowcreated2026-06-11updated2026-06-11dotnetloaderobfuscationbitmap-steganographyanti-vmevasionreflective-code-loading
SHA-256: db0d6bc0d73b6e2cf8dedde102e67ab2ad6233c9ff93f29be39351c1580dec8f

unclassified-dotnet-bitmap-stego-loader: db0d6bc0 — Purchase Order.exe, May 2022 sibling with 24 embedded bitmaps

Executive Summary: A .NET Framework PE32 loader masquerading as a purchase-order document. It carries ~24 small bitmap resources (76×76×24) that serve as encrypted payload carriers — a steganographic loader pattern previously observed in sibling 4bf14434 (Apr 2020). Reflective assembly loading, anti-VM Xen checks, and file-system discovery are statically confirmed by capa. No runtime IOCs recovered; payload logic lives inside the bitmap ciphertext. Static-only analysis — no CAPE detonation.

What It Is

Field Value
SHA-256 db0d6bc0d73b6e2cf8dedde102e67ab2ad6233c9ff93f29be39351c1580dec8f
Filename Purchase Order.exe
Size 927 744 bytes (906 KB)
Type PE32 executable (GUI) Intel 80386 Mono/.Net assembly, 3 sections ^[file.txt]
Timestamp Mon May 9 21:14:59 2022 UTC ^[pefile.txt:34]
Linker 8.0 (Visual Studio 2005-era) ^[pefile.txt:45]
InternalName KKKKK.exe ^[exiftool.json:40]
Version 24.11.37.197 ^[exiftool.json:39]
Signed No ^[rabin2-info.txt:27]
Imports mscoree.dll!_CorExeMain only ^[pefile.txt:254]

Second confirmed sibling in the unclassified-dotnet-bitmap-stego-loader cluster. Compared to 4bf14434 (Apr 2020, version 21.19.1.278, internal name dgnjtnhgjf.exe, ~20 bitmaps), this sample shifts to a May 2022 build, version 24.11.37.197, internal name KKKKK.exe, and carries ~24 embedded bitmaps. The core technique — bitmap-embedded payload steganography via System.Resources.ResourceReader — is unchanged.

How It Works

  1. Resource extraction — At runtime the loader opens its own PE resource stream using System.Resources.ResourceReader / RuntimeResourceSet and iterates over embedded System.Drawing.Bitmap objects. ^[strings.txt:3048] ^[strings.txt:3051]
  2. Bitmap steganography — Binwalk identifies ~24 sequential PC bitmap structures (76×76×24) in .rsrc starting at offset 0x7640E. ^[binwalk.txt] These are not display assets; their pixel channels likely carry an encrypted payload. The exact cipher and key are not recoverable statically.
  3. Reflective loading — Once decrypted/decompressed, the payload is loaded in-memory via System.Reflection.Assembly.LoadGetMethodInvoke. Capa flags invoke .NET assembly method and T1620 Reflective Code Loading. ^[capa.txt]
  4. Anti-VM — Capa detects anti-VM strings targeting Xen (reference anti-VM strings targeting Xen). ^[capa.txt] No explicit debugger checks were recovered in strings.
  5. File-system discoverycheck file extension in .NET, check if file exists, and File and Directory Discovery (T1083) are flagged by capa. ^[capa.txt]
  6. Thread / process control — Capa notes suspend thread and terminate process capabilities, suggesting payload-stage process/thread manipulation. ^[capa.txt]
  7. PRNG usegenerate random numbers in .NET (2 matches) implies the loader or its payload uses System.Random for key derivation, filename generation, or sandbox evasion. ^[capa.txt]

Decompiled Behavior

Radare2 analysis (level 2, 2318 functions) produced CIL stack-machine pseudocode for entry0 that is not meaningful for behavioral narrative without ILSpy-level decompilation. The binary is pure .NET CIL; native decompilers emit push/pop/switch stack operations rather than readable C#. Key behavioral evidence therefore comes from string extraction and capa capability detection.

Notable recovered API references from strings:

  • GetManifestResourceStream ^[strings.txt:4559]
  • Invoke ^[strings.txt:4284]
  • GetMethod ^[strings.txt:4234]
  • CreateInstance ^[strings.txt:4263]
  • Activator ^[strings.txt:4787]
  • Random ^[strings.txt:4571]
  • Thread ^[strings.txt:4207]
  • StreamWriter ^[strings.txt:4771]
  • ComponentResourceManager ^[strings.txt:4761]
  • CheckBox, DataGridViewCheckBoxColumn, FormStartPosition ^[strings.txt:4983] — WinForms UI elements suggesting a fake GUI lure or builder-generated stub.

C2 Infrastructure

No hardcoded C2 endpoints, domains, IP addresses, or mutex names recovered. All network logic is expected to reside in the bitmap-encrypted inner payload. Network indicators require dynamic detonation or manual bitmap extraction + decryption.

Interesting Tidbits

  • Masquerade naming — "Purchase Order.exe" is a classic business-lure social-engineering filename. The version-info block claims nonsense company/product names (9<32E8>2<I98JC>9HD<CAF?, A3;A?7F@:GC9I7=D;:24) — the same obfuscation pattern seen in the Apr 2020 sibling. ^[exiftool.json]
  • Builder fingerprint — The presence of ComponentResourceManager, CheckBox, DataGridViewCheckBoxColumn, and FormStartPosition suggests a Visual Studio WinForms designer-generated stub or a builder that compiles from a Visual Basic/C# WinForms template. ^[strings.txt]
  • Version progression21.19.1.27824.11.37.197 over ~2 years. The author maintains a versioned build pipeline.
  • Static-only — CAPE skipped because no Windows guest is available. All inferences above are static; runtime behavior (actual C2, payload family, persistence) is unconfirmed.

How To Mess With It (Homelab Replication)

Goal: reproduce a .NET bitmap-stego loader that passes capa's access .NET resource + invoke .NET assembly method fingerprint.

Toolchain: Visual Studio 2022 Community, .NET Framework 4.8, C# WinForms.

  1. Create a C# WinForms project. Add 20+ small BMP files (76×76×24) as Embedded Resource.
  2. In Program.cs, replace the normal form launch with:
using System;
using System.IO;
using System.Reflection;
using System.Resources;
using System.Drawing;

byte[] payload = null;
var asm = Assembly.GetExecutingAssembly();
foreach (var name in asm.GetManifestResourceNames()) {
    using (var stream = asm.GetManifestResourceStream(name)) {
        using (var bmp = new Bitmap(stream)) {
            // XOR pixel data with a key derived from PRNG seed
            payload = ExtractAndDecrypt(bmp);
        }
    }
}
var inner = Assembly.Load(payload);
inner.EntryPoint.Invoke(null, new object[] { });
  1. Compile Release/x86. Run capa repro.exe and confirm hits on access .NET resource, invoke .NET assembly method, generate random numbers in .NET.
  2. Verification: compare capa namespace matches to this sample's capa.txt.

Deployable Signatures

YARA rule

rule UNCLASSIFIED_DOTNET_BITMAP_STEGO_LOADER {
    meta:
        description = ".NET loader with embedded bitmap resources and reflective assembly loading"
        author = "PacketPursuit"
        date = "2026-06-11"
        sha256 = "db0d6bc0d73b6e2cf8dedde102e67ab2ad6233c9ff93f29be39351c1580dec8f"
    strings:
        $bitmap = "System.Drawing.Bitmap" wide ascii
        $resource = "System.Resources.ResourceReader" wide ascii
        $manifest = "GetManifestResourceStream" wide ascii
        $invoke = "Invoke" wide ascii
        $reflection = "System.Reflection" wide ascii
        $bmp_magic = { 42 4D }  // "BM" — PC bitmap header
    condition:
        uint16(0) == 0x5A4D and
        $bitmap and
        $resource and
        $manifest and
        $invoke and
        $reflection and
        // Presence of multiple BM headers in .rsrc (heuristic for embedded bitmaps)
        #bmp_magic >= 10
}

Behavioral hunt query (Sigma-like)

title: .NET Bitmap-Stego Loader Execution
logsource:
    category: process_creation
    product: windows
detection:
    selection:
        CommandLine|contains:
            - 'Purchase Order.exe'
            - 'KKKKK.exe'
        Image|endswith: '.exe'
    condition: selection

IOC list

Indicator Value Type
SHA-256 db0d6bc0d73b6e2cf8dedde102e67ab2ad6233c9ff93f29be39351c1580dec8f hash
Filename Purchase Order.exe filename
Internal name KKKKK.exe version-info
Version 24.11.37.197 version-info
Company name 9<32E8>2<I98JC>9HD<CAF? masquerade

Behavioral fingerprint

A .NET PE32 GUI executable with only mscoree.dll!_CorExeMain in its import table, carrying 20+ small BMP resources in .rsrc. At launch it enumerates manifest resources, extracts System.Drawing.Bitmap objects, decrypts a hidden payload from their pixel data, and reflectively loads it via System.Reflection.Assembly.Load + Invoke. Anti-VM Xen checks and file-system extension probing are present. No network indicators in the outer binary.

Detection Signatures

ATT&CK Technique Evidence Source
T1620 Reflective Code Loading invoke .NET assembly method, Assembly.Load inference ^[capa.txt]
T1497.001 Virtualization/Sandbox Evasion::System Checks anti-VM Xen strings ^[capa.txt]
T1083 File and Directory Discovery file extension / existence checks ^[capa.txt]
T1036.002 Masquerading fake version-info with nonsense strings ^[exiftool.json]
C0021.003 Generate Pseudo-random Sequence::Use API PRNG use flagged by capa ^[capa.txt]
C0052 Writes File .NET file write capability ^[capa.txt]
C0055 Suspend Thread thread suspension flagged ^[capa.txt]
C0018 Terminate Process process termination flagged ^[capa.txt]

References

  • Artifact ID: acc4b6f2-c5a4-4e69-bfef-e0912f35b7c7
  • Source: OpenCTI / MalwareBazaar
  • Sibling analysis: /intel/analyses/4bf14434ef61c6da79d3e5e4ea7831a4e5f0a2769cccdb41ddcc7ca0920e640a.html
  • Wiki entity: unclassified-dotnet-bitmap-stego-loader

Provenance

Analysis derived from:

  • file.txt (file type identification)
  • exiftool.json (PE metadata / version-info)
  • pefile.txt (PE header / sections / imports)
  • strings.txt (static string extraction)
  • floss.txt — tool invocation failed; no decoded strings recovered
  • capa.txt (Mandiant flare-capa v7 static capability detection)
  • binwalk.txt (embedded bitmap enumeration)
  • rabin2-info.txt (radare2 binary header summary)
  • dynamic-analysis.md — CAPE skipped, no Windows guest available
  • radare2 MCP: analyze level 2, list_all_strings, decompile_function entry0