マルウェアでよく使われる共通API
Reading time: 13 minutes
tip
AWSハッキングを学び、実践する:
HackTricks Training AWS Red Team Expert (ARTE)
GCPハッキングを学び、実践する:
HackTricks Training GCP Red Team Expert (GRTE)
Azureハッキングを学び、実践する:
HackTricks Training Azure Red Team Expert (AzRTE)
HackTricksをサポートする
- サブスクリプションプランを確認してください!
- **💬 Discordグループまたはテレグラムグループに参加するか、Twitter 🐦 @hacktricks_liveをフォローしてください。
- HackTricksおよびHackTricks CloudのGitHubリポジトリにPRを提出してハッキングトリックを共有してください。
一般
ネットワーク
| Raw Sockets | WinAPI Sockets |
|---|---|
| socket() | WSAStratup() |
| bind() | bind() |
| listen() | listen() |
| accept() | accept() |
| connect() | connect() |
| read()/recv() | recv() |
| write() | send() |
| shutdown() | WSACleanup() |
TLS pinning and chunked transport
多くのローダーは TCP ストリームを SslStream でラップし、サーバのリーフ証明書を埋め込みコピーと突き合わせて固定(certificate pinning)します。Bot 情報やタスクは圧縮されることが多い(例: GZip)。レスポンスが閾値(約 1 MB)を超えると、サイズベースのヒューリスティックを回避し、デシリアライズ時のメモリスパイクを抑えるためにデータを小さなチャンク(例: 16 KB セグメント)に分割します。
Persistence
| Registry | File | Service |
|---|---|---|
| RegCreateKeyEx() | GetTempPath() | OpenSCManager |
| RegOpenKeyEx() | CopyFile() | CreateService() |
| RegSetValueEx() | CreateFile() | StartServiceCtrlDispatcher() |
| RegDeleteKeyEx() | WriteFile() | |
| RegGetValue() | ReadFile() |
Encryption
| Name |
|---|
| WinCrypt |
| CryptAcquireContext() |
| CryptGenKey() |
| CryptDeriveKey() |
| CryptDecrypt() |
| CryptReleaseContext() |
Anti-Analysis/VM
| Function Name | Assembly Instructions |
|---|---|
| IsDebuggerPresent() | CPUID() |
| GetSystemInfo() | IN() |
| GlobalMemoryStatusEx() | |
| GetVersion() | |
| CreateToolhelp32Snapshot [Check if a process is running] | |
| CreateFileW/A [Check if a file exist] |
Locale/keyboard-based execution guard
多くの stealer/loader は特定のロケールで動作を中断して研究者を回避したり、脅威アクターの制約に従ったりします。典型的なチェック:
GetKeyboardLayoutでインストールされているレイアウトを列挙(スレッド/ユーザ単位)GetLocaleInfoA/Wで国/地域コードを取得GetSystemDefaultLangID/GetUserDefaultLangID
もしブロックリスト(一般的には CIS 諸国)が一致すると、ローダーはネットワーク IOCs やインジェクションを行う前に即座に終了します。
Defence/hunting
- 実行の早い段階で複数のロケール/キーボード API を問い合わせて即座に終了するプロセスをフラグ化する。
- BIOS 文字列、PnP デバイス、ディスクモデル、サービスなど、オープンソースプロジェクト(例: VMDetector)から流用された anti-VM チェックと相関させ、ゲートされた実行を検出する。
Emulator API fingerprinting & sleep evasion
マルウェアはしばしば Defender の仮想化されたエクスポート(Malware Protection Emulator で見られる)を検索してサンドボックスエミュレータを指紋化します。これらのシンボルが存在する場合(プロセスの大文字小文字を区別しないスキャン)、解析時間を浪費するために実行を 10〜30 分遅延させて再チェックします。
canary として使われる API 名の例:
MpVmp32Entry,MpVmp32FastEnter,MpCallPreEntryPointCode,MpCallPostEntryPointCode,MpFinalize,MpReportEvent*,MpSwitchToNextThread*VFS_*ファミリ:VFS_Open,VFS_Read,VFS_MapViewOfFile,VFS_UnmapViewOfFile,VFS_FindFirstFile/FindNextFile,VFS_CopyFile,VFS_DeleteFile,VFS_MoveFileThrdMgr_*:ThrdMgr_GetCurrentThreadHandle,ThrdMgr_SaveTEB,ThrdMgr_SwitchThreads
Typical delay primitive (user-land):
cmd /c timeout /t %RANDOM_IN_[600,1800]% > nul
Argument gatekeeping
- オペレーターはしばしば、ペイロードを実行する前に見た目が無害なCLIスイッチが存在することを要求します(例:
/i:--type=rendererは Chromium の子プロセスを模倣するため)。そのスイッチが無ければ、ローダーは直ちに終了し、単純なサンドボックス実行を妨げます。
ステルス
| 名前 | |
|---|---|
| VirtualAlloc | メモリを確保 (packers) |
| VirtualProtect | メモリの権限を変更 (セクションに実行権を与えるpacker) |
| ReadProcessMemory | 外部プロセスへの注入 |
| WriteProcessMemoryA/W | 外部プロセスへの注入 |
| NtWriteVirtualMemory | |
| CreateRemoteThread | DLL/プロセス注入... |
| NtUnmapViewOfSection | |
| QueueUserAPC | |
| CreateProcessInternalA/W |
実行
| Function Name |
|---|
| CreateProcessA/W |
| ShellExecute |
| WinExec |
| ResumeThread |
| NtResumeThread |
その他
- GetAsyncKeyState() -- Key logging
- SetWindowsHookEx -- Key logging
- GetForeGroundWindow -- 実行中のウィンドウ名を取得(またはブラウザからサイト名を取得)
- LoadLibrary() -- ライブラリの読み込み
- GetProcAddress() -- ライブラリの関数取得
- CreateToolhelp32Snapshot() -- 実行中プロセスの一覧取得
- GetDC() -- スクリーンショット
- BitBlt() -- スクリーンショット
- InternetOpen(), InternetOpenUrl(), InternetReadFile(), InternetWriteFile() -- インターネットアクセス
- FindResource(), LoadResource(), LockResource() -- 実行ファイルのリソースへアクセス
マルウェア手法
DLL Injection
Execute an arbitrary DLL inside another process
- 悪意あるDLLを注入するプロセスを特定する: CreateToolhelp32Snapshot, Process32First, Process32Next
- プロセスを開く: GetModuleHandle, GetProcAddress, OpenProcess
- プロセス内にDLLのパスを書き込む: VirtualAllocEx, WriteProcessMemory
- 悪意あるDLLをロードするスレッドをプロセス内に作成する: CreateRemoteThread, LoadLibrary
使用されるその他の関数: NTCreateThreadEx, RtlCreateUserThread
Reflective DLL Injection
Load a malicious DLL without calling normal Windows API calls.
DLLはプロセス内にマップされ、インポートアドレスを解決し、リロケーションを修正し、DllMain関数を呼び出します。
Thread Hijacking
プロセスのスレッドを見つけ、そのスレッドに悪意あるDLLをロードさせる
- ターゲットスレッドを見つける: CreateToolhelp32Snapshot, Thread32First, Thread32Next
- スレッドを開く: OpenThread
- スレッドを停止する: SuspendThread
- 被害プロセス内に悪意あるDLLのパスを書き込む: VirtualAllocEx, WriteProcessMemory
- ライブラリをロードさせるためにスレッドを再開する: ResumeThread
PE Injection
Portable Execution Injection: 実行ファイルを被害プロセスのメモリに書き込み、そこから実行されます。
Process Hollowing (a.k.a RunPE)
Process Hollowing は Windows マルウェアでよく使われる 防御回避 / 実行 トリックの一つです。考え方は、正規のプロセスを suspended 状態で起動し、その元のイメージをメモリから取り除き(hollow)、任意の PE をその場所にコピーするというものです。プライマリスレッドが再開されると、悪意あるエントリポイントが信頼されたバイナリ(しばしば Microsoft によって署名されている)になりすまして実行されます。
典型的なワークフロー:
- 無害なホスト(例:
RegAsm.exe,rundll32.exe,msbuild.exe)を suspended 状態で生成し、まだ命令が実行されないようにする。
STARTUPINFOA si = { sizeof(si) };
PROCESS_INFORMATION pi;
CreateProcessA("C:\\Windows\\Microsoft.NET\\Framework32\\v4.0.30319\\RegAsm.exe",
NULL, NULL, NULL, FALSE, CREATE_SUSPENDED, NULL, NULL, &si, &pi);
- 悪意あるペイロードをメモリに読み込み、そのPEヘッダを解析して
SizeOfImage、セクション、そして新しいEntryPointを取得する。 - NtUnmapViewOfSection / ZwUnmapViewOfSection – サスペンドされたプロセスの元のイメージベースをアンマップする。
- VirtualAllocEx – リモートプロセス内に
SizeOfImage分のRWXメモリを確保する。 - WriteProcessMemory – まず
Headersをコピーし、その後セクションを反復してそれらの raw data をコピーする。 - SetThreadContext – コンテキスト構造体内の
EAX/RAX(RCXは x64) またはRipの値をパッチし、EIPがペイロードのEntryPointを指すようにする。 - ResumeThread – スレッドが続行し、攻撃者の提供したコードを実行する。
Minimal proof-of-concept (x86) skeleton:
void RunPE(LPCSTR host, LPVOID payload, DWORD payloadSize){
// 1. create suspended process
STARTUPINFOA si = {sizeof(si)}; PROCESS_INFORMATION pi;
CreateProcessA(host, NULL,NULL,NULL,FALSE,CREATE_SUSPENDED,NULL,NULL,&si,&pi);
// 2. read remote PEB to get ImageBaseAddress
CONTEXT ctx; ctx.ContextFlags = CONTEXT_FULL;
GetThreadContext(pi.hThread,&ctx);
PVOID baseAddr;
ReadProcessMemory(pi.hProcess,(PVOID)(ctx.Ebx+8),&baseAddr,4,NULL);
// 3. unmap original image & allocate new region at same base
NtUnmapViewOfSection(pi.hProcess,baseAddr);
PVOID newBase = VirtualAllocEx(pi.hProcess,baseAddr,pHdr->OptionalHeader.SizeOfImage,
MEM_COMMIT|MEM_RESERVE,PAGE_EXECUTE_READWRITE);
// 4-5. copy headers & sections …
// 6. write new image base into PEB and set Eip
WriteProcessMemory(pi.hProcess,(PVOID)(ctx.Ebx+8),&baseAddr,4,NULL);
ctx.Eax = (DWORD)(newBase) + pHdr->OptionalHeader.AddressOfEntryPoint;
SetThreadContext(pi.hThread,&ctx);
// 7. run!
ResumeThread(pi.hThread);
}
「DarkCloud Stealer」キャンペーンで観測された実務上の注意点:
- loader はホストとして
RegAsm.exe(.NET Framework の一部)を選択した — 署名済みバイナリで注意を引きにくい。 - 復号された VB6 stealer (
holographies.exe) はディスクにドロップされず、常に hollowed process の内部にのみ存在するため静的検出が困難。 - 機密文字列(regexes、paths、Telegram credentials)は各文字列ごとに RC4-encrypted され、実行時にのみ復号されるためメモリスキャンがさらに困難になる。
検出のアイデア:
- GUI/コンソールウィンドウを一切作成せず、メモリ領域が RWX として割り当てられるまで
CREATE_SUSPENDEDプロセスをアラートする(正規のコードでは稀)。 - 異なるプロセス間での呼び出しシーケンス
NtUnmapViewOfSection ➜ VirtualAllocEx ➜ WriteProcessMemoryを検出する。 - 信頼された開発ユーティリティを hollowing hosts として異常に使用する点、特に
MSBuild.exe、RegAsm.exe、rundll32.exeが短命の loaders によって親子付けされるケースに注意。 - ユーザー書き込み可能なパスから生成された、または対応する
.sln/.projコンテキストなしに起動し、その後アウトバウンド接続を行うmsbuild.exeを追跡する(ATT&CK T1127.001 + T1055.012)。
Common host processes and path resolution
MSBuild.exeは開発ツールと同化するために hollowing host として頻繁に選ばれる。Loaders はアーキテクチャに適した場所を検索することが多い:C:\Windows\Microsoft.NET\Framework\v4.0.30319\MSBuild.exeC:\Windows\Microsoft.NET\Framework64\v4.0.30319\MSBuild.exeC:\Windows\System32\MSBuild.exeC:\Windows\SysWOW64\MSBuild.exe- CreateProcess(..., CREATE_SUSPENDED, ...) を呼び出す前に、現在の payload/OS のアーキテクチャに一致するホストを選択する。
Hooking
- SSDT (System Service Descriptor Table) はカーネル関数 (ntoskrnl.exe) や GUI ドライバ (win32k.sys) へのポインタを指しており、ユーザープロセスがこれらの関数を呼び出せるようにする。
- rootkit はこれらのポインタを攻撃者が制御するアドレスに変更する可能性がある。
- IRP (I/O Request Packets) はコンポーネント間でデータ片を伝送する。カーネル内のほとんど全てが IRP を使用しており、各デバイスオブジェクトは独自の関数テーブルを持ち、これが hook 可能:DKOM (Direct Kernel Object Manipulation)
- IAT (Import Address Table) は依存関係を解決するのに有用。呼び出されるコードをハイジャックするためにこのテーブルを hook することが可能。
- EAT (Export Address Table) Hooks。これらの hook は userland から行える。目的は DLL によってエクスポートされた関数を hook すること。
- Inline Hooks: このタイプは実現が難しい。関数自身のコードを修正することを伴う。例えば関数の先頭にジャンプを置くなど。
参考資料
- Unit42 – New Infection Chain and ConfuserEx-Based Obfuscation for DarkCloud Stealer
- Check Point Research – Under the Pure Curtain: From RAT to Builder to Coder
- Unit 42 – PhantomVAI Loader Delivers a Range of Infostealers
- MITRE ATT&CK – Trusted Developer Utilities Proxy Execution: MSBuild (T1127.001)
- VMDetector – virtualization checks (open-source)
tip
AWSハッキングを学び、実践する:
HackTricks Training AWS Red Team Expert (ARTE)
GCPハッキングを学び、実践する:
HackTricks Training GCP Red Team Expert (GRTE)
Azureハッキングを学び、実践する:
HackTricks Training Azure Red Team Expert (AzRTE)
HackTricksをサポートする
- サブスクリプションプランを確認してください!
- **💬 Discordグループまたはテレグラムグループに参加するか、Twitter 🐦 @hacktricks_liveをフォローしてください。
- HackTricksおよびHackTricks CloudのGitHubリポジトリにPRを提出してハッキングトリックを共有してください。
HackTricks