Project VOIDLENS is a security-sensitive Windows desktop static analyzer for explaining what an untrusted executable or installer appears capable of doing. Its central promise is simple: submitted samples are never executed and never uploaded during local analysis.
⚠️ Work in progress — not a finished product. Project VOIDLENS is under active development. Most of the pipeline now exists and is tested — isolation, PE/CLR analysis, capability rules, nested-artifact discovery, reporting, and the desktop UI — and an isolated analysis now completes end to end (see Current status), but MSI analysis, YARA-X, packaging, and CI are unimplemented. Nothing here is production-ready, and no security claim should be relied upon yet.
These examples show the intended output once capability analysis is fully wired. They illustrate the report's shape and language — they are not produced by the current build.
Project VOIDLENS reports capabilities in terms of the exact imports, strings, and IL it found, never as claims about what a file "did." Each line expands to the precise evidence — imported APIs, decoded strings, call sites, byte offsets — and an evidence tier, so a reviewer can check every claim.
Verdict: High-risk static indicators · Analysis: Complete within v1 policy
- Discord targeting — pulls information from Discord and restarts the Discord client; collects Discord account and friend information
- Credential access — decrypts passwords and browser data from Chrome-style browsers; decrypts Firefox passwords through Firefox's NSS system; reads browser cookies and login databases
- Filesystem discovery & staging — searches through Desktop and Documents; collects files for exfiltration
- Data exfiltration & C2 — uploads collected files; receives remote commands over an encrypted WebSocket connection
- Surveillance — takes screenshots; accesses the webcam
- Process manipulation — kills processes; injects code into another process; spoofs process information to help hide what was running
- Privilege & tokens — impersonates Windows security tokens
- Persistence & system config — reads and changes the Windows Registry
- Destructive behavior — encrypts, renames, overwrites, and truncates files
Recommended action: do not run the file; verify its provenance or escalate to a qualified reviewer.
Verdict: Few material static concerns identified · Analysis: Complete within v1 policy
- Valid Authenticode signature; Windows platform trust verified the signer
- Network use limited to update checks over HTTPS to the vendor's own domain
- No credential-store access, process injection, surveillance, or destructive capabilities found by the enabled checks
No material concerns were identified by the enabled static checks. This does not rule out malicious behavior, downloaded components, environment-dependent actions, or vulnerabilities outside VOIDLENS's rules. Do not run a file solely because this result is favorable.
Project VOIDLENS never labels a file "safe" outright — it reports what the enabled checks did and did not find, and always shows how complete the analysis was.
An implementation checkpoint — not yet production-ready, and not yet usable. The pipeline components are built and tested (503 tests: 403 unit, 93 security, 7 integration, 0 skipped), but the desktop application cannot currently complete a scan, and the format coverage and distribution work listed below remains incomplete. The test count measures the components, not a working product.
The worker-truncation defect that previously stopped any scan from completing is
fixed and validated on Windows. Intake handles are now opened with
FILE_SYNCHRONOUS_IO_NONALERT (and the SYNCHRONIZE access right that flag
requires), so the handle the worker inherits matches the synchronous reads it
performs. What that validation covers, precisely:
- ✅
HandleChainTests.Analysis_DoesNotDisposeTheCallersLease— previously skipped as the reproducer, now runs and passes. It performs a real isolated analysis: intake opens a sample, the broker launches the AppContainer worker against that borrowed handle, and the returned artifact's SHA-256 matches the lease. The status is asserted not to beIsolationUnavailable. - ⬜ That test's sample is a 128-byte synthetic MZ stub, so it proves the intake → broker → worker → contract chain carries a result. It is not evidence about analysis depth or robustness on real-world binaries.
- ❌ The desktop application still cannot complete a scan. A manual run against
C:\Windows\System32\notepad.exereproduced the same SHA-256 in the UI but returnedIsolationUnavailable/Withheld. The cause is deterministic composition, not an AppContainer fault:MainWindowconstructs a defaultWorkerBrokerwith no authenticated worker-package manifest, so the broker correctly fails closed. The app-level integration test drives a fake broker, which is why nothing caught it. - ⬜ Validated on one host only (Windows 11 Pro, build 26200). The release-gating OS matrix below is untouched.
Done so far:
-
Reproducible .NET 10 solution with bounded, immutable evidence/verdict contracts.
-
Single-handle file intake: opens the input read-only (deny write/delete sharing), records stable Windows identity, walks paths by held handle without following reparse points, and detects format by bytes rather than extension.
-
Fail-closed worker isolation: a capability-free AppContainer under a kill-on-close Job Object (one process, memory/CPU/wall-clock limits), launched suspended with a four-handle allowlist and a signed, hash-verified worker package. Token, SID, capabilities, Job limits, and mitigations are all verified before resume; any failure returns
IsolationUnavailablewith no ordinary-process fallback. A live security suite (using a generated probe, never malware) checks network, child-process, traversal, reparse, resource-limit, and handle denials. -
PE/CLR analysis: independent bounds-checked PE parsing cross-checked against AsmResolver, managed metadata read without loading the assembly, and cache-only, noninteractive Authenticode trust (offline revocation stays indeterminate, never "valid"). Parser faults are contained at the worker boundary and become incompleteness, never a crash or a favorable result.
-
Capability rules: nine curated rules matching imports and P/Invokes into evidence-cited findings. Import presence is not treated as proof of use, so findings are capped at structural evidence with
Referencedreachability, and ubiquitous patterns (debugger checks, dynamic API resolution, socket use) are tiered down so they read as context rather than accusation. An image whose imports cannot be read is forced incomplete — a packed sample that hid its import table withholds a verdict instead of scoring as the cleanest result available. -
Bounded nested-artifact discovery: a SHA-256-keyed artifact graph with an extraction budget (depth, count, total and per-artifact bytes, entries per container, expansion ratio) and an archive path policy covering traversal, rooted and UNC paths, reserved device names, alternate data streams, and control characters. Deduplicated entries are still charged to the budget, so repeating one payload buys no free expansion.
-
Reports: deterministic JSON and self-contained, script-free HTML under a restrictive CSP, with every evidence tier preserved, credential-shaped strings redacted by default, and an explicit full-evidence mode behind a privacy warning.
-
Desktop workflow: a WPF shell with browse/drag-drop intake, Quick/Deep modes, cancellation, capability cards that preserve evidence tiers, report export, and an explicit SHA-256-only VirusTotal lookup (confirmed per request, redirects denied, memory-only session key, and never an input to the verdict).
-
MSI analysis (in progress, 5 of 12 planned tasks): bounded MSI primitives and a compound-file preflight, custom-action decoding with UI/execute reachability, a read-only
msi.dllboundary restricted to an exact 13-function allowlist enforced by IL-level guards, and inventory of SummaryInformation plus the package-structure tables. Read-only database access was proven to work inside the capability-free AppContainer before the design was settled. Not yet reachable: MSI roots are not routed through the worker, so.msiinputs are still rejected as unsupported.
Not done yet: routing MSI through the worker, embedded-cabinet and nested-storage traversal, string extraction, ASAR/JAR readers, YARA-X, packaging, and CI. No security claim should be inferred from this checkpoint.
- Windows PE files:
.exe,.dll,.scr, and.sys - Windows Installer databases:
.msi
Nested content may eventually be identified and analyzed under explicit limits, but archives and other formats are not planned as root inputs. Unsupported or invalid roots will produce an incomplete/unsupported analysis, never a favorable verdict.
The intended trust boundaries are represented by the project graph:
RunOrNope.App (WPF presentation)
|-- Contracts / Core / Reporting
`-- Broker.Windows -- Intake
|
`-- restricted Worker (separate process)
|-- PE analyzer
|-- MSI analyzer
|-- content analyzer
`-- Rules
The WPF project deliberately has no reference to parser projects. The broker opens each sample once and passes only a duplicate of that existing handle to a capability-free AppContainer worker under Job Object limits. Hostile worker output crosses back only as bounded, validated contract data. Isolation failures fail closed.
- An x64 host listed in the build matrix below for release-gating work
- PowerShell
- The pinned .NET SDK 10.0.302
The target framework's windows10.0.19041.0 suffix is the minimum Windows API
contract available to compiled code. It is not a claim that every Windows build
from 19041 onward is supported.
| Edition | OS build | Foundation status |
|---|---|---|
| Windows 11 Pro | 26200 | Locally validated for SDK restore, Release build, and unit tests on x64 |
| Windows 10 Enterprise LTSC 2021 | 19044 | Release-gating target; not yet validated |
| Windows 11 Enterprise 24H2 | 26100 | Release-gating target; not yet validated |
| All other Windows editions and builds | Any | Unverified; no compatibility claim |
This foundation validation covers only restore, compilation, and the project graph test. Before a release, every release-gating target must pass the planned AppContainer, Job Object, mitigation-policy, WinTrust, read-only MSI, long-path, and enterprise-policy suites on a then-serviced patch level. The exact serviced revision and servicing state will be recorded in release evidence; until those gates exist and pass, Project VOIDLENS has no supported runtime configuration.
Install the repository-local SDK with Microsoft's official installer:
New-Item -ItemType Directory -Path .tools -Force | Out-Null
Invoke-WebRequest -Uri "https://dot.net/v1/dotnet-install.ps1" -OutFile ".tools\dotnet-install.ps1"
& .\.tools\dotnet-install.ps1 -Version "10.0.302" -InstallDir ".tools\dotnet" -NoPath
& .\.tools\dotnet\dotnet.exe --versionRestore, build, and test:
& .\.tools\dotnet\dotnet.exe restore
& .\.tools\dotnet\dotnet.exe build -c Release --no-restore
& .\.tools\dotnet\dotnet.exe test -c Release --no-buildLocked restore is enforced centrally, so an ordinary restore fails if a
dependency declaration and its committed lock file disagree. When deliberately
changing dependencies, regenerate lock files explicitly and review their diff:
& .\.tools\dotnet\dotnet.exe restore -p:RestoreLockedMode=false --force-evaluate
& .\.tools\dotnet\dotnet.exe restoreLocal analysis has no network feature and must not execute, load, install, repair, shell-open, preview, or resolve sample-controlled content. No file upload is planned or implemented.
The VirusTotal action is implemented as a separate, explicitly confirmed lookup that discloses only the SHA-256. Each request shows the exact hash and destination before anything is sent, redirects are refused, the response is size-bounded, and the API key is held in memory for the session only — never written to disk, a report, a log, or an exception. Its result is displayed in its own panel and is not an input to the static verdict: a clean or missing reputation result never improves a disposition.
Reports redact credential-shaped strings by default; full evidence is available behind an explicit privacy warning.
- The desktop application cannot complete a scan: it composes a broker without an
authenticated worker package and always returns
IsolationUnavailable. - MSI analysis exists as a tested analyzer but is not wired to the worker, so
.msiinputs are still rejected as unsupported. An MSI whose payload sits in an embedded cabinet is not yet forced incomplete — that is scheduled before MSI roots become reachable, so no favourable result can be produced from unexamined cabinet content. - Nested-artifact discovery has the graph, budget, and path policy but no container readers yet, so nothing is actually unpacked. String extraction is not implemented.
- Capability rules cover imports and P/Invokes only. There is no data-flow analysis, so no finding can reach "confirmed static implementation", and by design that caps every verdict below high risk.
- YARA-X is not integrated.
- The current Authenticode result covers Windows' primary embedded-signature policy result and structurally counts certificate records. Full signer, timestamp, secondary-signature, and catalog enumeration remains unfinished.
- Worker isolation and transport are implemented and locally security-tested, but release-gating OS/enterprise-policy validation is not complete.
- Release-gating OS targets have not yet completed runtime/security validation.
- The end-to-end chain is proven only by an automated test against a synthetic MZ stub, driven by an authenticated test worker package. The shipping application does not compose one, so no real scan has ever completed through the UI.
- No security claim should be inferred from this scaffold.
- ✅ Immutable, bounded evidence and verdict contracts.
- ✅ Single-handle intake with identity and mutation checks.
- ✅ Fail-closed AppContainer and Job Object worker isolation.
- ⏳ Read-only analysis — PE/CLR done; the nested-content graph and budget are done but have no container readers; MSI analysis is 5 of 12 tasks in and not yet routed through the worker.
- ⏳ Evidence-backed capability rules — import and P/Invoke rules done; YARA-X and data-flow-backed evidence not started.
- ✅ Script-free JSON/HTML reporting with privacy controls.
- ⏳ WPF workflow and accessibility done; packaging, CI, and security documentation not started.
- ✅ Worker-truncation defect fixed and validated on Windows: an isolated analysis completes end to end and the reproducer test passes.
- ⬜ Compose the application with an authenticated worker package so a scan can actually complete, and add a regression test against the real composition. This is the blocker between the current build and a usable tool.
- ⏳ Finish MSI: route roots through the worker, force incompleteness for unexpanded cabinets and nested storages, and prove real AppContainer MSI analysis.
- ⬜ Validate across the release-gating OS matrix.
Project VOIDLENS is released under the MIT License.
Project VOIDLENS builds on free, open-source components, and integrates established
open-source security tools rather than reinventing them. Every dependency's
license is recorded in THIRD-PARTY-NOTICES.md; all are
free to use and redistribute, and licenses are re-verified before each release.
- Currently bundled: AsmResolver.PE (MIT) for PE parsing; JsonSchema.Net (MIT).
- Test-only: AwesomeAssertions (Apache-2.0), xUnit (Apache-2.0), and the .NET test SDK (MIT). None ship in the application.
- Planned, license-cleared security integrations: YARA-X (BSD-3-Clause) with curated, versioned rule packs; innoextract (zlib) and 7-Zip (LGPL-2.1+) as isolated extraction adapters.
Malware-family detection (for example information-stealer families) is carried only as YARA rules and signatures that recognize those families. Project VOIDLENS never vendors malware samples or payloads into the repository or release artifacts.