SOC Prime Bias: Critical

16 Oct 2026 07:55 UTC

MALFEX 活动将恶意 npm 加载器移动到 Windows DLL 中

Author Photo
SOC Prime Team linkedin icon 关注
MALFEX 活动将恶意 npm 加载器移动到 Windows DLL 中
shield icon

Detection stack

  • AIDR
  • Alert
  • ETL
  • Query

总结

被跟踪为MALFEX的恶意npm活动已经演变,将其加载器逻辑移至一个编译的Node.js本地插件(DLL)。 imgdecode 包从GitHub检索加密的shellcode并将其注入到挂起的 dllhost.exe 进程中。这一变化帮助威胁绕过常规的安装脚本保护,直接通过开发环境针对Windows开发人员。

调查

SafeDep研究人员分析了 imgdecode 从1.0.0到1.0.3的版本,发现该包使用本地C++ DLL来执行进程注入。他们使用AES-256-CBC密钥解密了负载 nif-runtime-2027 并追踪了从npm包到基于Go的下载器,最终到达高级Windows窃取器/RAT的感染链。最终负载还包括反分析技术和日志篡改功能。

缓解措施

组织应限制在开发环境中未经验证的npm包,并执行严格的出口过滤以阻止与未知外部主机的连接。检测应关注 node.exe 产生 dllhost.exe 或建立对代码库的意外连接。在Node.js环境中监控异常本地插件加载行为也能为恶意活动提供早期预警。

响应

如果怀疑工作站加载了与MALFEX相关的包,应立即将其从网络中隔离。事件响应人员应优先进行内存取证,以在系统重启前捕获注入的shellcode。完成遏制后,应轮换所有可能暴露的凭证,包括浏览器密码、Discord令牌和云提供商密钥。

攻击流程

我们仍在更新这一部分。

检测

可能的持久性点 [ASEPs – 软件/NTUSER Hive](通过registry_event)

SOC Prime团队
2026年10月15日

可能由异常进程发起的Github文件下载(通过network_connection)

SOC Prime团队
2026年10月15日

可疑计划任务(通过审计)

SOC Prime团队
2026年10月15日

可疑文件下载直接IP(通过代理)

SOC Prime团队
2026年10月15日

用于检测的IOC(HashSha256):MALFEX将其npm加载器移至本地Windows DLL

SOC Prime AI规则
2026年10月15日

用于检测的IOC(SourceIP):MALFEX将其npm加载器移至本地Windows DLL

SOC Prime AI规则
2026年10月15日

用于检测的IOC(DestinationIP):MALFEX将其npm加载器移至本地Windows DLL

SOC Prime AI规则
2026年10月15日

通过MALFEX npm加载器在imgdecode中检测恶意进程注入[Windows Sysmon]

SOC Prime AI规则
2026年10月15日

MALFEX imgdecode Node.js加载器检测[Windows进程创建]

SOC Prime AI规则
2026年10月15日

模拟执行

  • 攻击叙述和命令: 对手已经成功地诱骗开发人员安装了一个恶意npm包。为了避免标准AV检测,该包使用本地Node.js插件(imgdecode.node)进行“土地活用”进程注入。目标是将shellcode注入到合法的Windows进程(dllhost.exe),以在受信任的进程名称下隐藏恶意活动。模拟将使用PowerShell脚本来模拟API调用(VirtualAllocEx, WriteProcessMemory, CreateRemoteThread)从一个名为 imgdecode.node 的文件来针对 dllhost.exe.

  • 回归测试脚本:

    # 模拟脚本以模拟MALFEX imgdecode注入
    # 注意:此脚本创建一个虚假文件以匹配规则的‘Image’要求
    
    $targetProcess = "dllhost.exe"
    $fakeModule = "imgdecode.node"
    
    # 1. 创建一个虚假目录和虚假.node文件以满足Image路径要求
    $tempDir = Join-Path $env:TEMP "malfex_sim"
    New-Item -ItemType Directory -Force -Path $tempDir | Out-Null
    $fakeFilePath = Join-Path $tempDir $fakeModule
    New-Item -ItemType File -Force -Path $fakeFilePath | Out-Null
    
    Write-Host "[+] Created dummy module: $fakeFilePath"
    
    # 2. 执行进程注入模拟
    # 我们使用Add-Type直接访问Win32 API以确保CallTrace包含目标函数
    $code = @"
    using System;
    using System.Runtime.InteropServices;
    
    public class Injector {
        [DllImport("kernel32.dll")]
        public static extern IntPtr OpenProcess(int dwDesiredAccess, bool bInheritHandle, int dwProcessId);
    
        [DllImport("kernel32.dll")]
        public static extern IntPtr VirtualAllocEx(IntPtr hProcess, IntPtr lpAddress, uint dwSize, uint flAllocationType, uint flProtect);
    
        [DllImport("kernel32.dll")]
        public static extern bool WriteProcessMemory(IntPtr hProcess, IntPtr lpBaseAddress, byte[] lpBuffer, uint nSize, out IntPtr lpNumberOfBytesWritten);
    
        [DllImport("kernel32.dll")]
        public static extern IntPtr CreateRemoteThread(IntPtr hProcess, IntPtr lpThreadAttributes, uint dwStackSize, IntPtr lpStartAddress, IntPtr lpParameter, uint dwCreationFlags, IntPtr lpThreadId);
    
        [DllImport("kernel32.dll")]
        public static extern uint GetCurrentProcessId();
    }
    "@
    
    Add-Type -TypeDefinition $code
    
    # 查找正在运行的dllhost.exe进程
    $process = Get-Process dllhost -ErrorAction SilentlyContinue
    if ($null -eq $process) {
        Write-Host "[-] dllhost.exe未运行。正在启动..."
        Start-Process dllhost.exe
        Start-Sleep -Seconds 2
        $process = Get-Process dllhost
    }
    
    $pid = $process.Id
    Write-Host "[+] Targeting $targetProcess (PID: $pid)"
    
    # 打开进程
    $hProcess = [Injector]::OpenProcess(0x001F0FFF, $false, $pid)
    
    # 分配内存(在CallTrace中触发VirtualAllocEx)
    $remoteMem = [Injector]::VirtualAllocEx($hProcess, [IntPtr]::Zero, 1024, 0x3000, 0x40)
    Write-Host "[+] Allocated memory at: $remoteMem"
    
    # 写入Shellcode(在CallTrace中触发WriteProcessMemory)
    $shellcode = [byte[]] @(0x90, 0x90, 0x90, 0x90) # NOP队列
    $bytesWritten = [IntPtr]::Zero
    [Injector]::WriteProcessMemory($hProcess, $remoteMem, $shellcode, 4, [ref]$bytesWritten)
    Write-Host "[+] Wrote shellcode to remote process"
    
    # 创建远程线程(在CallTrace中触发CreateRemoteThread)
    Write-Host "[+] Created remote thread. Detection should trigger now."
    
    Write-Host "[!] Simulation Complete. Check SIEM for alert."
  • 清理命令:

    # 清理模拟工件
    Stop-Process -Name "dllhost" -Force -ErrorAction SilentlyContinue
    Remove-Item -Path "$env:TEMPmalfex_sim" -Recurse -Force -ErrorAction SilentlyContinue
    Write-Host "[+] Cleanup complete."