Skip to content

VNX-511: Logic/Time Bomb: destructive action gated on a hard-coded date

Detects a condition comparing the current time with a hard-coded date that guards file deletion, a shell command or code evaluation. Python, JavaScript and TypeScript.

Updated 02 Nov 2026Checked against cli@de9b52a
Field Value
Rule ID VNX-511
Severity Medium
SARIF level warning
Kind sast
Languages JavaScript / TypeScript, Python
CWE CWE-511
CAPEC CAPEC-66
ATT&CK T1190
CWSS vector CWSS:1.0/TI:M/AP:RU/AL:S/IC:N/FC:LT/RP:RU/RL:S/AV:L/AS:N/IN:A/SC:A/BI:M/DI:H/EX:M/EC:N/P:C
Tags logic-time-bomb malicious-code cwe-511
Source internal/sast/rules/vnx-511.rego

Overview

VNX-511 maps to CWE-511: Logic/Time Bomb. A time bomb is code that does nothing harmful until a date passes, which is why it survives review and testing. The rule reports the if that compares the current time with a fixed date when the block it guards (the same line, or up to eight deeper-indented lines below) deletes files, runs a shell command or evaluates code. The current time can be read on the condition line or through a variable assigned only the current time within ten lines above (now = datetime.now(timezone.utc), const today = new Date()).

  • Python: datetime.now()/utcnow()/today() (with or without a time zone), date.today() or time.time() compared with datetime(20xx, ...), date(20xx, ...), a string that is a "20xx-mm-dd" date, .year against 20xx, or a 10-digit epoch; guarding os.remove/unlink/rmdir/removedirs, shutil.rmtree, os.system/popen, subprocess, exec/eval or os.kill.
  • JavaScript/TypeScript: Date.now() or new Date() (also .getFullYear()) compared with new Date('20xx...'), new Date(20xx, ...), Date.parse('20xx...'), a 13-digit epoch, or a constant the file assigns such a date; guarding fs.rm/rmSync/unlink/unlinkSync/rmdir/writeFileSync (also on fs.promises or an fs alias, and await rm()/unlink()), child_process exec/execSync/execFile/spawn/fork (bare or on a cp/child/childProcess receiver), eval, process.kill or rimraf.

What Gets Flagged

if datetime.now() > datetime(2026, 3, 1):          # FLAGGED
    shutil.rmtree("/srv/app/data", ignore_errors=True)
if (Date.now() >= 1798761600000) execSync('rm -rf ~/.ssh');   // FLAGGED

const CUTOFF = new Date("2026-12-31T00:00:00Z");
if (Date.now() > CUTOFF.getTime()) {                           // FLAGGED
  fs.rmSync(root, { recursive: true });
}

What Is Not Flagged

  • Date checks that only warn, log, raise or return (deprecation notices, certificate expiry).
  • Age comparisons with no fixed date (time.time() - os.path.getmtime(path) > MAX_AGE), including on a file whose name merely contains a date ("2024-01-01.log").
  • The pattern in comments or string literals.

Remediation

  1. Find out who added the condition and why; a legitimate scheduled cleanup belongs in a scheduler or configuration, not a hard-coded date in code.
  2. Remove the trigger, or replace it with an explicit, documented and reviewed configuration value.

References

Suppressing this rule

Put a nosec comment on the line, or on line 1 to cover the whole file. Use the comment marker of the file’s language (#, //, -- or ;):

# nosec vnx-511
// nosec vnx-511

Or record an ignore rule: vulnetix ignore add --rule vnx-511 --reason "...". See Suppressing findings.

Edit this pageSources: cli/internal/sast/rules/vnx-511.rego, cli/internal/sast/docs/vnx-511.md
esc
↑ ↓ move↵ openSearches in your browser. A key like autonomy.max or a code like threshold_required jumps straight to it.