LausivLoader — Multi-Stage JS / PowerShell / .NET Loader HuntPack
Executive Summary
LausivLoader is a multi-stage Windows malware loader documented by the SANS Internet Storm Center (Jan Kopriva, diary 33348, published 2026-09-17, last updated 2026-09-22). It arrives as a purchase-quotation spearphishing lure carrying an obfuscated JavaScript file inside a .r01 archive. The attacker's objective is to establish durable logon persistence disguised as a Microsoft Edge Update task, then stage a four-layer loader chain — JavaScript → PowerShell → first .NET loader → second .NET downloader — that ultimately hides its final payload inside a PNG image's iTXt metadata chunk, decoding it into a .NET assembly or native EXE that is executed via reflection or process hollowing.
The single most distinctive TTP is how the JavaScript hands decode instructions to PowerShell: instead of hardcoding file paths on the command line, the JS stage sets variables in its own process environment, which the intermediate conhost.exe --headless process and the child powershell.exe process inherit. This defeats naive analysis that extracts only the decoded PowerShell command line, and it means the file paths and decode context never appear together in any single visible artifact.
Highest-value defensive angle: because the payload content and the env-var handoff itself are not independently visible in standard Falcon process telemetry, this pack leans on process lineage (script host → conhost.exe --headless → PowerShell) and the scheduled task masquerade (MicrosoftEdgeUpdateTaskCore) as the highest-fidelity, lowest-FP detection surface — both are structurally unusual regardless of how the payload content is obfuscated.
Defender priority: the env-var handoff, in-memory AMSI patch, RC4/AES/GZip/DEFLATE transforms, and the final reflective-load/process-hollowing step are not independently visible via standard Falcon process/file events — do not rely on payload-content inspection. Hunt the process-lineage and persistence signatures in §8 first; treat any hit as high-priority triage given how few legitimate reasons exist to produce this lineage.
Source Review & Web Hunter Notes
| Tier | Source | Key Finding | Carry Forward |
|---|---|---|---|
| 1 (Primary) | SANS ISC diary 33348 — Jan Kopriva | Full technical analysis: delivery, all four stages, persistence mechanism, all three sample hashes, C2 URL, and the handlers' own 18-item MITRE ATT&CK mapping | Yes |
| 3 (Syndication) | malware.news repost | Forum mirror linking back to the SANS diary; no independent technical content | No (redundant, checked for divergence only) |
| 3 (AI-summarized aggregator) | OffSeq Threat Radar | Automated summary of the same diary; independently assigns Severity: medium | Partial (severity cue only) |
| 1 (same organization) | SANS Stormcast, 2026-09-18 — Johannes Ullrich | Same-organization audio corroboration of the diary's findings; no new IOCs, no retraction | Partial (authenticity/no-retraction check) |
All four sources trace back to the same author and organization (Jan Kopriva / SANS ISC) — no independent second research organization has corroborated this sample as of 2026-09-23. Per standing practice, prevent/critical-severity action requires two independent sources; because this intel is effectively single-sourced, every atomic IOC in this pack ships at detect/hunt tier only, never prevent, until a second source (a different vendor write-up, or your own telemetry) corroborates it.
Decisions made: the specific lure filename and .r01 archive extension were converted to behavioral patterns (double-dot-before-extension, multi-volume archive) rather than shipped as exact-match IOCs, since campaign-specific naming is expected to rotate on the next wave. All three published hashes and the yapw[.]life domain were kept as atomic IOCs (traced to source snapshot 01-sans-isc-diary.txt). No additional infrastructure, hashes, or actor attribution were invented beyond what the primary source published.
Hunt Brief & Attack Chain
Hunt hypotheses (ordered by fidelity)
| # | Hypothesis | MITRE | Falcon Events | FP Sources | Confidence |
|---|---|---|---|---|---|
| H1 | A script host (wscript.exe/cscript.exe) executes a .js file with a spoofed double extension delivered via an email/archive attachment | T1566.001, T1204.002, T1059.007 | ProcessRollup2 | Rare legitimate double-extension automation scripts | High |
| H2 | conhost.exe is spawned with an explicit --headless flag and a full path to powershell.exe embedded in its own command line, rather than acting as a normal console host | T1564.003, T1059.001 | ProcessRollup2 | Near zero — virtually no legitimate software invokes conhost.exe this way | High |
| H3 | Full lineage wscript.exe (grandparent) → conhost.exe --headless (parent) → powershell.exe -NoP -NonI -W Hidden -EncodedCommand (child) is the end-to-end fingerprint of this loader chain | T1059.001, T1059.007, T1564.003 | ProcessRollup2 | Very low | High |
| H4 | A scheduled task named MicrosoftEdgeUpdateTaskCore (or a similarly masquerading name) whose action executes a script host outside the legitimate Edge Update install path is LausivLoader's persistence | T1053.005, T1036.004 | ScheduledTaskRegistered | Low — genuine Edge Update tasks use different names/paths/executables | High |
| H5 | Logon-triggered re-execution of wscript.exe against %LOCALAPPDATA%\Microsoft\PhotoEngine\PhotoStudio.js indicates the persisted copy firing | T1053.005 | ProcessRollup2 | Low — non-standard path for that filename | Medium-High |
| H6 | DNS resolution or outbound connection to yapw[.]life or a PNG path resembling /phpt/stego_*.png indicates the stage-4 downloader reaching for the steganographic payload | T1105, T1027.003 | DnsRequest, NetworkConnectIP4 | Low, but this infrastructure is single-sourced and was already offline at publication — perishable | Medium |
| H7 | A PowerShell process launched with the exact flag combination -NoP -NonI -W Hidden -EncodedCommand and no other suspicious content (because the decode context rides in inherited env vars) is a broader, noisier signal for encoded-command execution generally | T1059.001 | ProcessRollup2 | Medium — many legitimate RMM/admin tools use hidden encoded PowerShell | Medium |
| H8 | AMSI-scan telemetry for -EncodedCommand PowerShell content immediately preceding the H1–H3 chain may catch the window before an AMSI-patch attempt succeeds | T1140, T1685 | ScriptControlScanTelemetry | High in isolation — only useful correlated with H2/H3 | Low-Medium |
Attack chain
| Step | Telemetry | Hunt Angle |
|---|---|---|
1. Spearphishing email with .r01 archive containing PO.4843293191 For Supply Chain - Imports HM..js; SPF/DMARC fail | Mail gateway logs | Native hunt (§7) |
2. User/automatic extraction; wscript.exe/cscript.exe executes the .js | ProcessRollup2 | Q1 |
3. JS builds a temp directory name from a random number + timestamp (base36) under %TEMP%, writes two encoded fragment files, sets environment variables (e.g. Kv7408/Kv562-style names) in its own process | Not independently visible — see §5/§15 gap | Coverage gap |
4. JS launches conhost.exe --headless "<path>\powershell.exe" -NoP -NonI -W Hidden -EncodedCommand <b64> | ProcessRollup2 | Q2 |
5. conhost.exe → powershell.exe inherits env vars, reads and deletes the two temp files, Base64-decodes, AES-128-CBC decrypts (embedded key/IV), GZip-decompresses → loads a 315,904-byte .NET assembly via Assembly.Load + entry-point invoke | Process lineage visible; in-memory decode is not | Q3 (lineage); gap for decode itself |
6. JS copies itself to %LOCALAPPDATA%\Microsoft\PhotoEngine\PhotoStudio.js and registers scheduled task \MicrosoftEdgeUpdateTaskCore via the Schedule.Service COM object (logon trigger; action = wscript.exe //B //Nologo <path>) | ScheduledTaskRegistered | Q4 |
| 7. Logon-triggered re-execution of the persisted JS | ProcessRollup2 | Q5 |
8. First .NET loader (315,904 bytes) resolves Windows APIs dynamically, attempts to patch AmsiScanBuffer/AmsiScanString, retains every 5th byte of an embedded 299,520-byte array, RC4-decrypts it → second .NET executable (59,904 bytes) | In-process patch + in-memory RC4; not independently visible | Coverage gap; Q8 partial pivot |
9. Second .NET downloader fetches hxxps://yapw[.]life/phpt/stego_zrgaixkku8.png, parses the PNG iTXt chunk, finds marker FF 89 AD 4A, XOR-decrypts and DEFLATE-decompresses → a PE (MZ) | DnsRequest, NetworkConnectIP4 | Q6 / Q7 |
| 10. Loader selects .NET reflection load (managed assembly) or process hollowing (native EXE) to run the final, unrecovered payload | Not independently visible — SANS never recovered the payload | Coverage gap |
Consolidated IOC Table
| Type | Value | Confidence | Action | Context | Expiry |
|---|---|---|---|---|---|
| sha256 | 408b2df6e81824fa5bdf4f0fbd185a7e6db06e2be98fbeebce416f66954b9fa9 | High | detect | Initial JS dropper, PO.4843293191 For Supply Chain - Imports HM..js | 2027-03-23 |
| md5 | 7acd5c5f1689332615c03357e143f51e | High | detect | Same JS dropper (MD5) | 2027-03-23 |
| sha256 | e4130bf8769a50106a963b6a43dfd4fe5b56c70eae76a0de971d25993159acfe | High | detect | First .NET loader / AMSI-patch stage, 315,904 bytes | 2027-03-23 |
| md5 | 5d92d1fb5d5fbd79a588f22e994a4aff | High | detect | Same first .NET loader (MD5) | 2027-03-23 |
| sha256 | be73e8b06c4356b5b4644d69b4f426bb3b32b4bf9f14cc5743f17532799f760b | High | detect | Second .NET downloader / PNG-stego stage, 59,904 bytes | 2027-03-23 |
| md5 | f351968c76eefc80d4e292a3f179b7b9 | High | detect | Same second .NET downloader (MD5) | 2027-03-23 |
| domain | yapw[.]life | Medium | hunt | Stage-4 PNG-steganography payload host; offline at publication, single-sourced | 2026-12-23 |
| url | hxxps://yapw[.]life/phpt/stego_zrgaixkku8.png | Medium | hunt | Exact payload URL; likely rotated after publication | 2026-12-23 |
| path (behavioral) | %LOCALAPPDATA%\Microsoft\PhotoEngine\PhotoStudio.js | Medium | hunt | Persisted copy of the JS dropper | 2026-12-23 |
| taskname | MicrosoftEdgeUpdateTaskCore | Medium | hunt | Masquerading scheduled task name; future campaigns will likely rename it | 2026-12-23 |
| behavioral | conhost.exe --headless launching powershell.exe | High | hunt | Distinctive JS-to-PowerShell handoff mechanism; durable TTP, not perishable infrastructure | 2027-03-23 |
Affected Surface & Telemetry Matrix
| Surface | Telemetry Required | Priority | Gap Risk |
|---|---|---|---|
| Windows endpoints (email-delivered scripts) | Falcon ProcessRollup2 / SyntheticProcessRollup2 (process execution + parent/grandparent lineage) | Critical | Low — well covered by Falcon |
| Windows Task Scheduler | Falcon ScheduledTaskRegistered; native Task Scheduler Operational log | High | Low |
| Email gateway | Native mail gateway logs (SPF/DMARC, attachment detonation) — outside Falcon entirely | High | High — Falcon has no native visibility; requires native audit hunt / email security tooling (§7) |
| In-memory .NET execution (reflective load, process hollowing, AMSI patch) | Falcon IOA/ML behavioral prevention (not raw CQL-queryable) | Critical | High — no raw event exposes the AMSI-patch bytes or the reflective Assembly.Load call itself |
| Process environment-variable inheritance (the handoff mechanism itself) | None — Falcon does not log per-process environment-variable contents | Medium (analysis value, not detection) | Full gap — explicitly flagged, not solvable with current telemetry |
| DNS / network egress | Falcon DnsRequest / NetworkConnectIP4 | Medium | Low visibility, low durability — single-sourced, perishable infrastructure |
ATT&CK Mapping
The following 18 techniques are the SANS ISC handler's own published mapping for this sample, cross-checked against the saved diary snapshot.
| Tactic | Technique | Behavior | Query / Control |
|---|---|---|---|
| Initial Access | T1566.001 Phishing: Spearphishing Attachment | Purchase-quotation lure with archived JS | Native hunt §7 |
| Execution | T1204.002 User Execution: Malicious File | Intended recipient execution of the extracted script | Q1 |
| Execution | T1059.007 Command and Scripting Interpreter: JavaScript | WSH executes the JS | Q1 |
| Execution | T1059.001 Command and Scripting Interpreter: PowerShell | JS constructs and executes a PowerShell command | Q2, Q3 |
| Persistence | T1053.005 Scheduled Task/Job: Scheduled Task | Logon task MicrosoftEdgeUpdateTaskCore | Q4 |
| Defense Evasion | T1036.004 Masquerading: Masquerade Task or Service | Task named like a legitimate Edge updater | Q4 |
| Defense Evasion | T1564.003 Hide Artifacts: Hidden Window | Hidden WScript.Shell launch, hidden PowerShell window, conhost --headless | Q2, Q3 |
| Defense Evasion | T1027.009 Obfuscated Files: Embedded Payloads | Embedded assemblies | Coverage gap |
| Defense Evasion | T1027.013 Obfuscated Files: Encrypted/Encoded File | Base64, AES-128-CBC, RC4 | Coverage gap |
| Defense Evasion | T1027.015 Obfuscated Files: Compression | GZipStream, DEFLATE | Coverage gap |
| Defense Evasion | T1027.016 Obfuscated Files: Junk Code Insertion | 450 nonfunctional comment lines | Native hunt §7 (static AV/YARA) |
| Defense Evasion | T1140 Deobfuscate/Decode Files or Information | Runtime decode/decrypt/decompress, interleaved-padding removal | Coverage gap |
| Defense Evasion | T1070.004 Indicator Removal: File Deletion | Deletes the two temp fragment files after use | Coverage gap |
| Defense Evasion | T1620 Reflective Code Loading | Assembly.Load(byte[]) + entry-point invoke in-process | Coverage gap (Falcon IOA/ML only) |
| Defense Evasion | T1685 Disable or Modify Tools | AMSI patch / ETW-redirect attempts | Q8 (partial pivot) |
| Command and Control | T1105 Ingress Tool Transfer | PNG download | Q6, Q7 |
| Defense Evasion | T1027.003 Obfuscated Files: Steganography | Payload hidden in the PNG iTXt chunk | Q6, Q7 (network layer only) |
| Defense Evasion | T1055.012 Process Injection: Process Hollowing | Conditional native-EXE execution branch | Coverage gap (Falcon IOA/Exploit Protection only) |
Native Audit-Log Hunts
Non-CQL checks for organizations without full Falcon coverage on a given surface, or as corroborating pivots.
- Email gateway: search inbound mail for multi-volume archive attachments (
.r00–.r99,.zip,.7z) containing script files, where SPF and/or DMARC evaluated to fail/none but the message was still delivered — that policy gap is exactly what let this sample through the sending gateway's own defenses. Cross-reference purchase-order / quotation lure language in the subject or body. - Task Scheduler Operational log (
Microsoft-Windows-TaskScheduler/Operational, Event ID 106 — task registered): filter for task names containingMicrosoftEdgeUpdateTaskCore, or for any task whose registering process is nottaskeng.exe/svchost.exe(a task registered via COM fromwscript.exeis anomalous). Note that genuine Edge Update tasks are namedMicrosoftEdgeUpdateTaskMachineCore/MicrosoftEdgeUpdateTaskMachineUA— the missing "Machine" segment is itself a naming mismatch worth flagging. - PowerShell Script Block Logging (Event ID 4104,
Microsoft-Windows-PowerShell/Operational): hunt decoded script-block content for AES/GZipStream/Assembly.Load/entry-point patterns, and correlate 4104 events whose parent chain includesconhost.exewith a--headlessflag. - Sysmon Event ID 1 (Process Create) — the same lineage hunt as Q3 for non-Falcon estates:
ParentImage=conhost.exeANDCommandLinecontains--headlessANDImage=powershell.exe. - Windows Defender Operational log (Event ID 1116/1117): any detection naming this family, or generic loader/heuristic detections on files under
%TEMP%\<random>\or%LOCALAPPDATA%\Microsoft\PhotoEngine\. - AMSI ETW telemetry (if instrumented): hunt for gaps in AMSI scan coverage for a PowerShell process immediately following the
conhost.exelineage — a missing AMSI scan record where one would normally be expected can indicate a successful patch ofAmsiScanBuffer/AmsiScanString.
CrowdStrike LogScale CQL Hunt Queries
Looks for: wscript.exe/cscript.exe executing a script whose name has a spoofed double extension immediately before .js/.vbs/.jse/.vbe — the LausivLoader lure pattern. FP: rare legitimate double-extension automation filenames.
// HUNT: Script Host Executing a Double-Extension Script // MITRE: T1566.001, T1204.002, T1059.007 // CONF: high // FP: medium // COST: low // REQUIRES: Falcon process telemetry (ProcessRollup2 / SyntheticProcessRollup2) // FALSE POSITIVES: legitimate installers or IT scripts that name files with double extensions (rare); vendor update wrapper scripts // TUNING: exclude known-good software-deployment paths (RMM script staging directories) and signed installer wrapper scripts once baselined // LOOKBACK: 7d #event_simpleName=/ProcessRollup2|SyntheticProcessRollup2/ | FileName=/^(wscript|cscript)\.exe$/i | CommandLine=/\.\.(js|jse|vbs|vbe)\b/i | table([ComputerName, UserName, FileName, ParentBaseFileName, CommandLine, TargetProcessId, aid, @timestamp])
Looks for: conhost.exe invoked directly with a --headless flag and a PowerShell target embedded in its own command line — the distinctive JS-to-PowerShell handoff mechanism. FP: essentially none observed; this is not how conhost.exe is normally invoked.
// HUNT: conhost.exe Launching PowerShell with --headless // MITRE: T1564.003, T1059.001 // CONF: high // FP: low // COST: low // REQUIRES: ProcessRollup2 // FALSE POSITIVES: none commonly observed; conhost.exe is not normally invoked directly against a target executable with --headless by legitimate software // TUNING: if a legitimate internal tool is found using this pattern, exclude it by SHA256HashData rather than by path (paths are trivially spoofable) // LOOKBACK: 7d #event_simpleName=/ProcessRollup2|SyntheticProcessRollup2/ | FileName=/^conhost\.exe$/i | CommandLine=/--headless/i | CommandLine=/powershell\.exe/i | table([ComputerName, UserName, ParentBaseFileName, FileName, CommandLine, TargetProcessId, ParentProcessId_decimal, aid, @timestamp])
Looks for: the complete three-generation process lineage (grandparent script host, parent conhost.exe --headless, child hidden/encoded PowerShell) in one query — the single highest-fidelity signature in this pack. FP: very low; requires all three unusual conditions to co-occur.
// HUNT: Full Chain Correlation - Script Host to conhost --headless to Encoded PowerShell // MITRE: T1059.007, T1059.001, T1564.003 // CONF: high // FP: low // COST: medium // REQUIRES: ProcessRollup2 with parent/grandparent lineage populated // FALSE POSITIVES: rare; some legitimate hidden automation also uses -W Hidden -EncodedCommand, but the wscript-to-conhost---headless grandparent lineage is highly unusual outside this loader family // TUNING: exclude known internal automation/RMM tooling that legitimately chains through conhost.exe in your environment, once confirmed benign ⚠ validate in tenant // LOOKBACK: 7d #event_simpleName=/ProcessRollup2|SyntheticProcessRollup2/ | FileName=/^powershell\.exe$/i | ParentBaseFileName=/^conhost\.exe$/i | GrandparentBaseFileName=/^(wscript|cscript)\.exe$/i | CommandLine=/-nop\b|-noprofile/i | CommandLine=/-w\s+hidden|-windowstyle\s+hidden/i | CommandLine=/-enc\b|-encodedcommand/i | table([ComputerName, UserName, GrandparentBaseFileName, ParentBaseFileName, FileName, CommandLine, TargetProcessId, aid, @timestamp])
Looks for: scheduled task registration matching the MicrosoftEdgeUpdateTaskCore masquerade name. FP: genuine Edge Update tasks are named MicrosoftEdgeUpdateTaskMachineCore/MicrosoftEdgeUpdateTaskMachineUA and run from Program Files, not a script host.
// HUNT: Scheduled Task Persistence Masquerading as Edge Update // MITRE: T1053.005, T1036.004 // CONF: high // FP: low // COST: low // REQUIRES: ScheduledTaskRegistered // FALSE POSITIVES: legitimate Edge Update tasks use the "TaskMachineCore"/"TaskMachineUA" names and Program Files paths; a task named like this with a script-host action is not legitimate // TUNING: if your fleet uses a custom deployment tool that names tasks similarly, add a !in(TaskExecutable, values=[...]) allowlist for your known-good updater binaries once baselined // LOOKBACK: 7d #event_simpleName=/ScheduledTaskRegistered/ | TaskName=/EdgeUpdateTaskCore/i | table([ComputerName, UserName, TaskName, TaskExecutable, TaskAuthor, aid, @timestamp])
Looks for: logon-triggered re-execution of the persisted JS copy from its non-standard install path. FP: none expected — PhotoEngine\PhotoStudio.js is not a legitimate Microsoft or Adobe component path.
// HUNT: wscript.exe Executing the Persisted Copy from PhotoEngine // MITRE: T1053.005, T1059.007 // CONF: high // FP: low // COST: low // REQUIRES: ProcessRollup2 // FALSE POSITIVES: none expected; PhotoEngine\PhotoStudio.js is not a legitimate Microsoft or Adobe component path // TUNING: if your environment has a legitimate application that installs under a "PhotoEngine" folder (unlikely), scope an exclusion to its known publisher/hash rather than the path // LOOKBACK: 7d #event_simpleName=/ProcessRollup2|SyntheticProcessRollup2/ | FileName=/^wscript\.exe$/i | CommandLine=/PhotoEngine\\PhotoStudio\.js/i | table([ComputerName, UserName, ParentBaseFileName, CommandLine, TargetProcessId, aid, @timestamp])
Looks for: DNS resolution of the reported stage-4 payload host. FP: none expected for this exact domain; however this indicator is single-sourced and was already offline at analysis time — treat a hit as high-priority triage, not confirmed active infrastructure.
// HUNT: DNS Resolution to the Stage-4 Payload Domain (yapw.life) // MITRE: T1105, T1027.003 // CONF: medium // FP: low // COST: low // REQUIRES: DnsRequest // FALSE POSITIVES: none expected for this specific domain; this indicator is perishable and single-sourced -- corroborate before treating a hit as confirmed compromise // TUNING: retire or re-verify this query once the domain is confirmed dead beyond the pack's expiry window (see section 4 IOC table) // LOOKBACK: 30d #event_simpleName=/DnsRequest/ | DomainName=/^(.*\.)?yapw\.life$/i | table([ComputerName, UserName, DomainName, ContextProcessId_decimal, aid, @timestamp])
Looks for: rare/first-seen HTTPS destinations reached directly by powershell.exe, as a baseline-rarity pivot toward the stage-4 downloader's PNG fetch (Falcon's NetworkConnectIP4 carries no HTTP path, so exact filename matching on stego_*.png requires a proxy/URL-aware log source). FP: high in isolation — any legitimate PowerShell HTTPS call (Windows Update helper scripts, package managers, cloud PowerShell modules) trips this; use it as a pivot after a Q1–Q3 hit, not standalone.
// HUNT: Rare Outbound HTTPS Destinations from a PowerShell Process // MITRE: T1105, T1027.003 // CONF: medium // FP: high // COST: medium // REQUIRES: NetworkConnectIP4 // FALSE POSITIVES: very high standalone -- legitimate PowerShell HTTPS calls (Windows Update, PSGallery, cloud provider modules, package managers) are common; this query has no URL/path visibility, only destination rarity // TUNING: do not alert on this standalone -- pivot from a Q6 hit, or once baselined exclude known-good SaaS/CDN ranges your PowerShell tooling normally reaches via !in()/!cidr() // LOOKBACK: 7d #event_simpleName=/NetworkConnectIP4/ | ContextBaseFileName=/^powershell\.exe$/i | RemotePort=443 | groupBy([RemoteAddressIP4], function=[count(as=Hits), collect(ComputerName, limit=5)], limit=1000) | sort(Hits, order=asc, limit=200)
Looks for: AMSI script-scan events tied to PowerShell, as circumstantial context for stage 3's AMSI-patch attempt (this shows content submitted to AMSI before any patch takes effect, not the patch itself). FP: very high in isolation — nearly all legitimate PowerShell/VBA activity generates AMSI scan telemetry; only meaningful time-correlated with a Q2/Q3 hit on the same host.
// HUNT: AMSI Script-Scan Telemetry Preceding a Hidden/Encoded PowerShell Launch // MITRE: T1140, T1685, T1059.001 // CONF: low-medium // FP: high // COST: medium // REQUIRES: ScriptControlScanTelemetry // FALSE POSITIVES: very high standalone -- almost all legitimate script execution generates AMSI scan telemetry; this only has value correlated to the process lineage in Q2/Q3 on the same aid within a short window // TUNING: do not run standalone -- join or time-correlate against Q3 hits on the same aid/TargetProcessId, and exclude your RMM/patch-management PowerShell modules once baselined // LOOKBACK: 7d #event_simpleName=/ScriptControlScanTelemetry/ | ContextBaseFileName=/^powershell\.exe$/i | table([ComputerName, UserName, ContextBaseFileName, aid, TargetProcessId, @timestamp])
CrowdStrike Custom IOA Recommendations
Q2, Q3, Q4, and Q5 have low enough false-positive profiles to promote to Custom IOAs. Q1, Q6, Q7, and Q8 stay as hunt/investigate-only queries (see §11 promotion criteria).
| IOA Name | Pattern | Exclusions | Deployment Path |
|---|---|---|---|
| Headless conhost PowerShell Launch | Any parent, FileName is conhost.exe, AND CommandLine contains --headless AND CommandLine contains powershell.exe | None known | Custom IOA rule, start in Detect-only for 2 weeks before Block (source: Q2) |
| Script-Host-to-PowerShell via conhost Chain | Grandparent wscript.exe/cscript.exe → parent conhost.exe --headless → child powershell.exe with hidden/encoded flags | Any confirmed internal automation using this exact chain (rare) — exclude by hash, not path | Custom IOA rule, Detect-only pilot first (source: Q3) |
| Edge-Update-Named Task Executing a Script Host | Task name matches EdgeUpdate*TaskCore/*TaskUA pattern AND the task action executable is wscript.exe/cscript.exe/powershell.exe (none appear in genuine Edge Update tasks) | Verify against your fleet's actual deployed Edge Update task hashes/paths once, before enabling Block | Custom IOA, can go to Block given near-zero legitimate overlap (source: Q4) |
| Persisted Script Execution from Non-Standard PhotoEngine Path | wscript.exe/cscript.exe executing any script under %LOCALAPPDATA%\Microsoft\PhotoEngine\ | Confirm no legitimate application installs there in your fleet | Block-capable after a 1-week Detect pilot (source: Q5) |
Machine-Readable IOC Appendix
type,value,action,severity,expiration,description,tags sha256,408b2df6e81824fa5bdf4f0fbd185a7e6db06e2be98fbeebce416f66954b9fa9,detect,high,2027-03-23,LausivLoader initial JS dropper,malware:LausivLoader md5,7acd5c5f1689332615c03357e143f51e,detect,high,2027-03-23,LausivLoader initial JS dropper (MD5),malware:LausivLoader sha256,e4130bf8769a50106a963b6a43dfd4fe5b56c70eae76a0de971d25993159acfe,detect,high,2027-03-23,LausivLoader first .NET loader / AMSI-patch stage,malware:LausivLoader md5,5d92d1fb5d5fbd79a588f22e994a4aff,detect,high,2027-03-23,LausivLoader first .NET loader (MD5),malware:LausivLoader sha256,be73e8b06c4356b5b4644d69b4f426bb3b32b4bf9f14cc5743f17532799f760b,detect,high,2027-03-23,LausivLoader second .NET downloader / PNG-stego stage,malware:LausivLoader md5,f351968c76eefc80d4e292a3f179b7b9,detect,high,2027-03-23,LausivLoader second .NET downloader (MD5),malware:LausivLoader domain,yapw.life,detect,medium,2026-12-23,LausivLoader stage-4 PNG-steganography payload host (offline at publication; single-sourced),malware:LausivLoader
# Behavioral indicators -- not literal atomic IOCs, hunt/detect on the pattern conhost.exe launched with --headless AND a powershell.exe path/args in its own CommandLine Process lineage: wscript.exe|cscript.exe -> conhost.exe (--headless) -> powershell.exe (-NoP -NonI -W Hidden -EncodedCommand) Scheduled task action = wscript.exe //B //Nologo <path>, task name masquerading as MicrosoftEdgeUpdateTaskCore wscript.exe executing a script under %LOCALAPPDATA%\Microsoft\PhotoEngine\ Script/archive filename containing a spoofed double extension immediately before .js/.vbs (e.g. "..js")
Malware family: LausivLoader (multi-stage JS / PowerShell / .NET loader) Stage 1: obfuscated JavaScript dropper (Windows Script Host) Stage 2: PowerShell loader (AES-128-CBC + GZipStream, in-memory .NET assembly load) Stage 3: .NET loader -- AMSI-patch attempt + RC4-decrypted embedded payload (315,904 bytes) Stage 4: .NET downloader -- PNG steganography payload via iTXt chunk, marker FF 89 AD 4A, XOR + DEFLATE (59,904 bytes) Persistence: scheduled task \MicrosoftEdgeUpdateTaskCore (Schedule.Service COM, logon trigger) Persisted copy path: %LOCALAPPDATA%\Microsoft\PhotoEngine\PhotoStudio.js Payload host (single-sourced, offline at publication): yapw.life/phpt/stego_zrgaixkku8.png
# Verify these controls are deployed BEFORE relying on detection alone
Get-MpPreference | Select-Object -ExpandProperty AttackSurfaceReductionRules_Ids
# confirm D3E037E1-3EB8-44C8-A917-57927947596D and 5BEB7EFE-FD9A-4556-801D-275E5FFC04CC are present, Actions = 1 (Block)
Get-ScheduledTask | Where-Object {$_.TaskName -like "*EdgeUpdate*"} | Select-Object TaskName, TaskPath, Actions
# confirm no non-Microsoft actions on any Edge Update task
(Get-ItemProperty 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ScriptBlockLogging' -ErrorAction SilentlyContinue).EnableScriptBlockLogging
# expect 1
Get-Service CSFalconService | Select-Object Name, Status
# expect Running
Detection Validation Gates
Telemetry ready: ProcessRollup2/SyntheticProcessRollup2, ScheduledTaskRegistered, DnsRequest, and NetworkConnectIP4 are all standard Falcon sensor telemetry, ready by default on any modern sensor policy with process and network visibility enabled.
Benign baseline: run Q1, Q3, and Q7 read-only over a 30-day lookback before enabling any Custom IOA in Block mode; confirm zero hits, or that every hit is fully explained by known RMM/deployment tooling.
Positive tests: do not execute the live sample. Validate detection logic instead: (a) in an isolated lab VM, manually invoke conhost.exe --headless "%windir%\System32\WindowsPowerShell\v1.0\powershell.exe" -NoP -NonI -W Hidden -Command "Write-Host test" and confirm Q2/Q3 fire; (b) register a benign test scheduled task named MicrosoftEdgeUpdateTaskCore with a wscript.exe action pointed at a harmless test script and confirm Q4 fires; (c) resolve a synthetic test domain in the same shape and confirm Q6's DnsRequest pattern match logic behaves as expected against your own test value.
Promotion criteria: Q2, Q3, Q4, Q5 → promote to Custom IOA in Detect mode after a clean 2-week benign baseline, then Block after a further clean 2-week pilot ring. Q1 and Q6 stay in Detect/hunt given their moderate-to-perishable FP profile. Q7 and Q8 remain investigate-only correlation pivots, never standalone alerts.
Hardening — Tiered
- ASR rule — Block JavaScript/VBScript from launching downloaded executable content (
D3E037E1-3EB8-44C8-A917-57927947596D) in Block mode. MITRE M1038. CIS Microsoft Windows Benchmark 18-9-47-5-1-6. Directly blocks the stage-1→stage-2 handoff pattern. - ASR rule — Block execution of potentially obfuscated scripts (
5BEB7EFE-FD9A-4556-801D-275E5FFC04CC) in Block mode. MITRE M1038, M1040. CIS 18-9-47-5-1-7. Targets the 450-junk-comment-line obfuscation technique directly. ⚠ Windows Defender AV must be active (or passive-mode alongside Falcon) for ASR to evaluate — confirm compatibility with your EDR vendor if Falcon is primary AV. - Enable PowerShell ScriptBlock Logging and Module Logging (Event ID 4104). MITRE M1047. CIS 18-9-100-2/18-9-100-3. Restores visibility into the decoded
-EncodedCommandcontent, even though the env-var payload paths themselves will not appear. - Block executable/script content from the email gateway for archive attachments containing script files (
.js/.vbs/.jse/.wsf) inside.zip/.r0x/.7zcontainers, and hard-fail delivery on SPF/DMARC failure. MITRE M1017, M1031, M1054. Client-side complement: ASR ruleBE9BA2D9-53EA-4CDC-84E5-9B1EEEE46550(Block executable content from email client and webmail).
- AppLocker/WDAC path rule blocking
wscript.exe/cscript.exeexecution from%TEMP%,%LOCALAPPDATA%, and archive-extraction staging paths for standard users; allow only signed/approved automation. MITRE M1038, M1033. ⚠ pilot ring first — some legitimate installers stage scripts in%TEMP%. - Audit and lock down Task Scheduler task creation via COM (
Schedule.Service) for non-admin users; review AD/GPO delegation on the\Microsoft\Windows\scheduled-task folders. MITRE M1018, M1022, M1047. - Restrict registry and Task Scheduler root write access; require elevation for new top-level task registration outside
\Microsoft\Windows\...paths. MITRE M1024, M1022.
- PowerShell Constrained Language Mode / WDAC-enforced PowerShell policy fleet-wide, removing free-form
-EncodedCommandfrom the standard user's effective capability set outside signed, allow-listed automation. MITRE M1042, M1038. ⚠ significant piloting required — breaks ad hoc admin scripting; needs a signed-script exception workflow. - DNS-layer filtering (block newly-registered/uncategorized domains for standard endpoints) to catch stage-4 payload hosts like
yapw[.]lifebefore the fact, independent of any single atomic IOC's inevitable rotation. MITRE M1021, M1037. Vendor best-practice (Cisco Umbrella / Cloudflare Gateway category policy). ⚠ best-practice, no formal CIS benchmark entry for third-party DNS filtering products.
Deployable Playbooks
Playbook: LausivLoader Delivery & Execution-Chain Hardening (T1566.001, T1059.007, T1027)
MITRE: T1566.001, T1059.007, T1027 → M1038, M1040, M1047
Estimated deploy time: 2–3 hours (Immediate tier), plus a 1-week Audit-mode pilot for the ASR rules
Prerequisites: Windows 10 1809+ / Server 2019+, Microsoft Defender Antivirus present (active or passive alongside Falcon), local admin / GPO management rights
Reboot required: No for ASR rules and logging (take effect on next policy refresh / new process); Yes only if PowerShell v2 is also being removed in the same maintenance window
Step 1 — Enable ASR rule: Block JS/VBScript from launching downloaded executable content
What it does: Defender blocks JavaScript/VBScript from launching downloaded executable content.
Why it works: directly interrupts the stage-1-to-stage-2 handoff this loader depends on.
$asrRule = 'D3E037E1-3EB8-44C8-A917-57927947596D' Set-MpPreference -AttackSurfaceReductionRules_Ids $asrRule -AttackSurfaceReductionRules_Actions AuditMode Write-Output "ASR rule $asrRule set to Audit -- review Event ID 1122 for 1 week before Block"
GPO path: Computer Configuration > Administrative Templates > Windows Components > Microsoft Defender Antivirus > Microsoft Defender Exploit Guard > Attack Surface Reduction > Configure Attack Surface Reduction rules
Verify:
$ids = (Get-MpPreference).AttackSurfaceReductionRules_Ids
$actions = (Get-MpPreference).AttackSurfaceReductionRules_Actions
for ($i = 0; $i -lt $ids.Count; $i++) { if ($ids[$i] -eq 'D3E037E1-3EB8-44C8-A917-57927947596D') { "Action: $($actions[$i]) (1=Block, 2=Audit, 6=WarnUser)" } }
After a clean 1-week audit period, flip to Block:
Set-MpPreference -AttackSurfaceReductionRules_Ids 'D3E037E1-3EB8-44C8-A917-57927947596D' -AttackSurfaceReductionRules_Actions Enabled
Rollback:
Set-MpPreference -AttackSurfaceReductionRules_Ids 'D3E037E1-3EB8-44C8-A917-57927947596D' -AttackSurfaceReductionRules_Actions Disabled
Prerequisites: Defender AV present. Reboot required: No. Rollback: shown above — immediate, no reboot needed.
Step 2 — Enable ASR rule: Block execution of potentially obfuscated scripts
What it does: Defender blocks scripts that use heavy obfuscation (matches the 450-junk-comment-line technique).
Why it works: targets the obfuscation layer directly, independent of the specific lure filename.
$asrRule = '5BEB7EFE-FD9A-4556-801D-275E5FFC04CC' Set-MpPreference -AttackSurfaceReductionRules_Ids $asrRule -AttackSurfaceReductionRules_Actions AuditMode Write-Output "ASR rule $asrRule set to Audit -- review Event ID 1122 for 1 week before Block"
Verify: same pattern as Step 1, substituting the rule GUID.
Monitor for false positives: Event ID 1121 (Block) / 1122 (Audit) in Microsoft-Windows-Windows Defender/Operational. If a legitimate obfuscated script (rare) trips it, add a targeted exclusion:
Add-MpPreference -AttackSurfaceReductionOnlyExclusions 'C:\Program Files\YourTool\script.js'
Rollback:
Set-MpPreference -AttackSurfaceReductionRules_Ids '5BEB7EFE-FD9A-4556-801D-275E5FFC04CC' -AttackSurfaceReductionRules_Actions Disabled
Prerequisites: Defender AV present. Reboot required: No. Rollback: shown above.
Step 3 — Enable PowerShell ScriptBlock and Module Logging
What it does: logs decoded PowerShell script-block content to Event ID 4104.
Why it works: the env-var handoff hides file paths from the command line, but the decoded script block executed inside PowerShell still lands in this log once decrypted in memory.
$sbl = 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ScriptBlockLogging' New-Item -Path $sbl -Force | Out-Null New-ItemProperty -Path $sbl -Name 'EnableScriptBlockLogging' -Value 1 -PropertyType DWORD -Force | Out-Null $ml = 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ModuleLogging' New-Item -Path $ml -Force | Out-Null New-ItemProperty -Path $ml -Name 'EnableModuleLogging' -Value 1 -PropertyType DWORD -Force | Out-Null Write-Output "ScriptBlock + Module logging enabled"
GPO path: Computer Configuration > Administrative Templates > Windows Components > Windows PowerShell > Turn on PowerShell Script Block Logging → Enabled; and ... > Turn on Module Logging → Enabled, modules = *
Verify:
(Get-ItemProperty 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ScriptBlockLogging' -ErrorAction SilentlyContinue).EnableScriptBlockLogging # expect 1 Get-WinEvent -LogName 'Microsoft-Windows-PowerShell/Operational' -MaxEvents 1 -ErrorAction SilentlyContinue
Rollback:
Remove-ItemProperty -Path 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ScriptBlockLogging' -Name 'EnableScriptBlockLogging' -ErrorAction SilentlyContinue Remove-ItemProperty -Path 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ModuleLogging' -Name 'EnableModuleLogging' -ErrorAction SilentlyContinue
Prerequisites: PowerShell 5.0+. Reboot required: No — applies to new PowerShell sessions immediately. Rollback: shown above, no reboot needed.
Step 4 — AppLocker path rule: block script hosts from staging/temp paths
What it does: denies wscript.exe/cscript.exe execution of scripts from %TEMP%, %LOCALAPPDATA%, and common archive-extraction staging directories for standard users.
Why it works: the delivery mechanism depends on the extracted JS running from exactly these paths; this closes the execution surface even if the ASR rules in Steps 1–2 are bypassed by a future variant.
# Run in an elevated PowerShell session; requires AppLocker policy already provisioned via GPO $rule = New-AppLockerPolicy -RuleType Path -User Everyone -Action Deny ` -PathCondition "%OSDRIVE%\Users\*\AppData\Local\Temp\*","%LOCALAPPDATA%\*" -Verbose Write-Output "Review the generated rule, then merge into your AppLocker GPO in AUDIT mode first"
GPO path: Computer Configuration > Windows Settings > Security Settings > Application Control Policies > AppLocker > Script Rules — add a Deny path rule scoped to Everyone, then explicitly allow your known-good automation by publisher or hash.
Verify:
Get-AppLockerPolicy -Effective -Xml | Select-String "AppData\\Local\\Temp"
Rollback:
# Remove the specific Deny rule GUID from the AppLocker GPO and run: gpupdate /force
Prerequisites: AppLocker policy infrastructure already provisioned (Application Identity service running); pilot ring with 2–4 weeks of Audit-mode logging before enforcing. Reboot required: No, but the Application Identity service must be running (a service restart, not a reboot). Rollback: shown above — remove the rule and force a GPO refresh; no reboot needed.
Deploying via your RMM
The scripts above are raw PowerShell. To wrap them for fleet deployment (admin check, error handling, custom-field writeback for compliance tracking, scheduled re-verification), hand them to your RMM deployment tooling and ask for a deployable package. Suggested custom-field schema: Hardening_LausivLoader_ASR_JSVBS, Hardening_LausivLoader_ASR_Obfuscated, Hardening_LausivLoader_PSLogging, Hardening_LausivLoader_AppLocker, Hardening_LausivLoader_LastChecked.
Containment Runbook
| Phase | Actions | Owner | Evidence |
|---|---|---|---|
| 1. Isolate (0–1h) | Network-contain the affected host in the Falcon console; disable (do not yet delete) the scheduled task \MicrosoftEdgeUpdateTaskCore via Falcon RTR or schtasks /Change /TN /DISABLE; suspend any compromised mailbox forwarding/inbox rules if this was the entry point | IR on-call | Falcon RTR session log, task export, mailbox rule audit |
| 2. Eradicate (1–4h) | Kill any live wscript.exe/conhost.exe/powershell.exe process matching the chain; delete the persisted copy %LOCALAPPDATA%\Microsoft\PhotoEngine\PhotoStudio.js; delete the scheduled task; search-and-purge the original email/attachment fleet-wide via the mail gateway; sweep for the three published hashes fleet-wide (Q1–Q5 plus a direct Falcon IOC search) | IR + endpoint engineering | RTR file/process listing, mail gateway purge report, fleet-wide hash-hit count |
| 3. Recover (4–24h) | Rotate credentials cached on the host if privilege-escalation or credential-theft indicators are found; re-enable network access only after a clean scan and a re-run of Q1–Q8 shows no further hits; restore from backup only if file/system integrity is in doubt | Endpoint engineering + desktop support | Post-remediation scan report, 48h clean Falcon detection history |
| 4. Lessons / Closeout (24–72h) | Confirm the §12 hardening controls (ASR rules, ScriptBlock logging, mail gateway policy) are deployed fleet-wide, not just on the affected host; file a tracking item for the still-unidentified final payload (never recovered by SANS — the download URL was already offline); update this HuntPack's Changelog if new intel on the final payload or additional infrastructure surfaces | Detection engineering | Hardening deployment report, updated Changelog entry |
Detection Coverage Map
| Technique | Behavior | CQL | IOA | Coverage |
|---|---|---|---|---|
| T1566.001 Phishing Attachment | Archive + JS lure | — | — | PARTIAL native/email hunt only, no Falcon query |
| T1204.002 User Execution | JS execution via WSH | Q1 | — | GOOD |
| T1059.007 JavaScript Execution | wscript/cscript runs the JS | Q1 | — | GOOD |
| T1059.001 PowerShell Execution | Encoded, hidden PowerShell | Q2, Q3 | IOA1, IOA2 | GOOD |
| T1564.003 Hidden Window | conhost --headless | Q2, Q3 | IOA1, IOA2 | GOOD |
| T1053.005 Scheduled Task | MicrosoftEdgeUpdateTaskCore | Q4 | IOA3 | GOOD |
| T1036.004 Masquerading | Edge-Update-styled task name | Q4 | IOA3 | GOOD |
| T1053.005 (re-execution) | Persisted JS fires at logon | Q5 | IOA4 | GOOD |
| Env-var inter-process handoff (no sub-technique) | Inherited process environment variables | — | — | GAP Falcon does not log per-process environment-variable contents; inferable only from surrounding lineage |
| T1027.009/.013/.015/.016 Obfuscation family | Junk comments, AES/RC4/GZip/DEFLATE | — | — | GAP in-memory transform, no raw event |
| T1140 Deobfuscate/Decode | Runtime decrypt/decompress | — | — | GAP |
| T1070.004 File Deletion | Delete of 2 temp fragment files | — | — | GAP no confirmed generic file-delete event in the current Falcon reference set for this pack; native Sysmon Event ID 23 may help |
| T1620 Reflective Code Loading | Assembly.Load in-memory | — | Falcon IOA/ML only | GAP |
| T1685 Disable or Modify Tools | AMSI patch attempt | Q8 (pivot only) | — | PARTIAL |
| T1105 Ingress Tool Transfer | PNG download | Q6, Q7 | — | GOOD (perishable infrastructure) |
| T1027.003 Steganography | Payload hidden in PNG iTXt | Q6, Q7 (network layer only) | — | PARTIAL we see the fetch, not the extraction |
| T1055.012 Process Hollowing | Conditional native-EXE execution | — | Falcon IOA/Exploit Protection only | GAP |
See §11 for the full validation-gate procedure (telemetry readiness, benign baseline, safe positive testing, and promotion criteria) governing when Q2, Q3, Q4, and Q5 move from Detect to Block.
Hunt Summary Ticket
TITLE: LausivLoader -- Multi-Stage JS/PowerShell/.NET Loader Hunt
SEVERITY: Medium (single primary source; technically high-fidelity)
SCOPE: Windows endpoints with email/script-host exposure; Falcon-monitored fleet
HYPOTHESIS: A script host (wscript.exe/cscript.exe) launches a JS lure that hands
decode context to PowerShell via inherited environment variables through
an intermediate conhost.exe --headless process, then persists via a
scheduled task masquerading as Microsoft Edge Update, before staging a
4-layer loader chain that fetches a steganographic PNG payload.
QUERIES: Q1-Q8 (section 8); IOA1-IOA4 (section 9)
DO FIRST: Run Q3 (full chain correlation) and Q4 (scheduled task masquerade) --
highest fidelity, lowest FP, cover both the execution chain and the
persistence mechanism independently of payload content.
FINDINGS: [populate after first run -- host count, hit count, confirmed vs. FP]
GAPS: Env-var handoff itself, in-memory AES/RC4/GZip/DEFLATE transforms, AMSI
patch bytes, and the final reflective-load/process-hollowing step are not
independently visible via standard Falcon telemetry (see section 15).
Final payload family was never recovered by the primary source.
ACTIONS: Deploy section 12 Immediate-tier hardening (2 ASR rules, PS logging, mail
gateway attachment policy) this week; run section 11 benign baseline
before promoting Q2/Q3/Q4/Q5 to Custom IOA Block mode.
OWNER: HuntPack / detection engineering
VERSION: v0.1 -- 2026-09-23
Changelog
References
| Tier | Source | Used For | Access Date |
|---|---|---|---|
| 1 | SANS ISC diary 33348 — "LausivLoader analysis, or how to pass data between malware stages" (Jan Kopriva) | Primary technical analysis, full IOC set, the handlers' own ATT&CK mapping | 2026-09-23 |
| 1 | SANS Stormcast, 2026-09-18 (Johannes Ullrich) | Same-organization corroboration / no-retraction check | 2026-09-23 |
| 3 | malware.news repost | Syndication check — confirmed no divergent detail | 2026-09-23 |
| 3 | OffSeq Threat Radar summary | AI-generated severity triage cue ("medium") | 2026-09-23 |
| — | MITRE ATT&CK Mitigations reference | M-code citations in section 12 (M1017, M1018, M1021, M1022, M1024, M1031, M1033, M1037, M1038, M1040, M1042, M1047, M1054) | 2026-09-23 |
| — | Microsoft Defender ASR rules reference | ASR rule GUIDs used in the hardening playbook | 2026-09-23 |
| — | CIS Microsoft Windows Benchmark (controls 18-9-47-5-1-6, 18-9-47-5-1-7, 18-9-47-5-1-10, 18-9-100-2, 18-9-100-3) | Hardening control citations, via the HuntPack-Pipeline threat-hardening-v2 reference set | 2026-09-23 |