@cyclonedx/cdxgen 12.3.3 → 12.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (157) hide show
  1. package/README.md +64 -22
  2. package/bin/audit.js +21 -7
  3. package/bin/cdxgen.js +238 -116
  4. package/bin/convert.js +28 -13
  5. package/bin/hbom.js +490 -0
  6. package/bin/repl.js +580 -29
  7. package/bin/validate.js +34 -4
  8. package/bin/verify.js +40 -5
  9. package/data/README.md +298 -25
  10. package/data/component-tags.json +6 -0
  11. package/data/crypto-oid.json +16 -0
  12. package/data/predictive-audit-allowlist.json +11 -0
  13. package/data/queries-darwin.json +12 -1
  14. package/data/queries-win.json +7 -1
  15. package/data/queries.json +39 -2
  16. package/data/rules/ai-agent-governance.yaml +16 -0
  17. package/data/rules/asar-archives.yaml +150 -0
  18. package/data/rules/chrome-extensions.yaml +8 -0
  19. package/data/rules/ci-permissions.yaml +42 -18
  20. package/data/rules/container-risk.yaml +14 -7
  21. package/data/rules/dependency-sources.yaml +11 -0
  22. package/data/rules/hbom-compliance.yaml +325 -0
  23. package/data/rules/hbom-performance.yaml +307 -0
  24. package/data/rules/hbom-security.yaml +248 -0
  25. package/data/rules/host-topology.yaml +165 -0
  26. package/data/rules/mcp-servers.yaml +18 -3
  27. package/data/rules/obom-runtime.yaml +907 -22
  28. package/data/rules/package-integrity.yaml +14 -0
  29. package/data/rules/rootfs-hardening.yaml +179 -0
  30. package/data/rules/vscode-extensions.yaml +9 -0
  31. package/lib/audit/index.js +209 -8
  32. package/lib/audit/index.poku.js +332 -0
  33. package/lib/audit/reporters.js +222 -0
  34. package/lib/audit/targets.js +146 -1
  35. package/lib/audit/targets.poku.js +186 -0
  36. package/lib/cli/asar.poku.js +328 -0
  37. package/lib/cli/index.js +506 -88
  38. package/lib/cli/index.poku.js +1352 -212
  39. package/lib/evinser/evinser.js +14 -9
  40. package/lib/helpers/analyzer.js +1406 -29
  41. package/lib/helpers/analyzer.poku.js +342 -0
  42. package/lib/helpers/analyzerScope.js +712 -0
  43. package/lib/helpers/asarutils.js +1556 -0
  44. package/lib/helpers/asarutils.poku.js +443 -0
  45. package/lib/helpers/auditCategories.js +12 -0
  46. package/lib/helpers/auditCategories.poku.js +32 -0
  47. package/lib/helpers/cbomutils.js +271 -1
  48. package/lib/helpers/cbomutils.poku.js +248 -5
  49. package/lib/helpers/display.js +291 -1
  50. package/lib/helpers/display.poku.js +149 -0
  51. package/lib/helpers/evidenceUtils.js +58 -0
  52. package/lib/helpers/evidenceUtils.poku.js +54 -0
  53. package/lib/helpers/exportUtils.js +9 -0
  54. package/lib/helpers/gtfobins.js +142 -8
  55. package/lib/helpers/gtfobins.poku.js +24 -1
  56. package/lib/helpers/hbom.js +710 -0
  57. package/lib/helpers/hbom.poku.js +496 -0
  58. package/lib/helpers/hbomAnalysis.js +268 -0
  59. package/lib/helpers/hbomAnalysis.poku.js +249 -0
  60. package/lib/helpers/hbomLoader.js +35 -0
  61. package/lib/helpers/hostTopology.js +803 -0
  62. package/lib/helpers/hostTopology.poku.js +363 -0
  63. package/lib/helpers/inventoryStats.js +69 -0
  64. package/lib/helpers/inventoryStats.poku.js +86 -0
  65. package/lib/helpers/lolbas.js +19 -1
  66. package/lib/helpers/lolbas.poku.js +23 -0
  67. package/lib/helpers/osqueryTransform.js +47 -0
  68. package/lib/helpers/osqueryTransform.poku.js +47 -0
  69. package/lib/helpers/plugins.js +349 -0
  70. package/lib/helpers/plugins.poku.js +57 -0
  71. package/lib/helpers/protobom.js +156 -45
  72. package/lib/helpers/protobom.poku.js +140 -5
  73. package/lib/helpers/remote/dependency-track.js +36 -3
  74. package/lib/helpers/remote/dependency-track.poku.js +44 -0
  75. package/lib/helpers/source.js +24 -0
  76. package/lib/helpers/source.poku.js +32 -0
  77. package/lib/helpers/utils.js +1438 -93
  78. package/lib/helpers/utils.poku.js +846 -4
  79. package/lib/managers/binary.e2e.poku.js +367 -0
  80. package/lib/managers/binary.js +2293 -353
  81. package/lib/managers/binary.poku.js +1699 -1
  82. package/lib/managers/docker.js +201 -79
  83. package/lib/managers/docker.poku.js +337 -12
  84. package/lib/server/server.js +2 -27
  85. package/lib/stages/postgen/annotator.js +38 -0
  86. package/lib/stages/postgen/annotator.poku.js +107 -1
  87. package/lib/stages/postgen/auditBom.js +121 -18
  88. package/lib/stages/postgen/auditBom.poku.js +1366 -31
  89. package/lib/stages/postgen/hostTopologyAudit.poku.js +186 -0
  90. package/lib/stages/postgen/postgen.js +192 -1
  91. package/lib/stages/postgen/postgen.poku.js +321 -0
  92. package/lib/stages/postgen/ruleEngine.js +116 -0
  93. package/lib/stages/pregen/envAudit.js +14 -3
  94. package/package.json +23 -21
  95. package/types/bin/hbom.d.ts +3 -0
  96. package/types/bin/hbom.d.ts.map +1 -0
  97. package/types/bin/repl.d.ts.map +1 -1
  98. package/types/lib/audit/index.d.ts +44 -0
  99. package/types/lib/audit/index.d.ts.map +1 -1
  100. package/types/lib/audit/reporters.d.ts +16 -0
  101. package/types/lib/audit/reporters.d.ts.map +1 -1
  102. package/types/lib/audit/targets.d.ts.map +1 -1
  103. package/types/lib/cli/index.d.ts +16 -0
  104. package/types/lib/cli/index.d.ts.map +1 -1
  105. package/types/lib/evinser/evinser.d.ts +4 -0
  106. package/types/lib/evinser/evinser.d.ts.map +1 -1
  107. package/types/lib/helpers/analyzer.d.ts +33 -0
  108. package/types/lib/helpers/analyzer.d.ts.map +1 -1
  109. package/types/lib/helpers/analyzerScope.d.ts +11 -0
  110. package/types/lib/helpers/analyzerScope.d.ts.map +1 -0
  111. package/types/lib/helpers/asarutils.d.ts +34 -0
  112. package/types/lib/helpers/asarutils.d.ts.map +1 -0
  113. package/types/lib/helpers/auditCategories.d.ts +5 -0
  114. package/types/lib/helpers/auditCategories.d.ts.map +1 -1
  115. package/types/lib/helpers/cbomutils.d.ts +3 -2
  116. package/types/lib/helpers/cbomutils.d.ts.map +1 -1
  117. package/types/lib/helpers/display.d.ts.map +1 -1
  118. package/types/lib/helpers/evidenceUtils.d.ts +8 -0
  119. package/types/lib/helpers/evidenceUtils.d.ts.map +1 -0
  120. package/types/lib/helpers/exportUtils.d.ts.map +1 -1
  121. package/types/lib/helpers/gtfobins.d.ts +8 -0
  122. package/types/lib/helpers/gtfobins.d.ts.map +1 -1
  123. package/types/lib/helpers/hbom.d.ts +49 -0
  124. package/types/lib/helpers/hbom.d.ts.map +1 -0
  125. package/types/lib/helpers/hbomAnalysis.d.ts +62 -0
  126. package/types/lib/helpers/hbomAnalysis.d.ts.map +1 -0
  127. package/types/lib/helpers/hbomLoader.d.ts +7 -0
  128. package/types/lib/helpers/hbomLoader.d.ts.map +1 -0
  129. package/types/lib/helpers/hostTopology.d.ts +12 -0
  130. package/types/lib/helpers/hostTopology.d.ts.map +1 -0
  131. package/types/lib/helpers/inventoryStats.d.ts +11 -0
  132. package/types/lib/helpers/inventoryStats.d.ts.map +1 -0
  133. package/types/lib/helpers/lolbas.d.ts.map +1 -1
  134. package/types/lib/helpers/osqueryTransform.d.ts +3 -0
  135. package/types/lib/helpers/osqueryTransform.d.ts.map +1 -1
  136. package/types/lib/helpers/plugins.d.ts +58 -0
  137. package/types/lib/helpers/plugins.d.ts.map +1 -0
  138. package/types/lib/helpers/protobom.d.ts +3 -4
  139. package/types/lib/helpers/protobom.d.ts.map +1 -1
  140. package/types/lib/helpers/remote/dependency-track.d.ts +10 -3
  141. package/types/lib/helpers/remote/dependency-track.d.ts.map +1 -1
  142. package/types/lib/helpers/source.d.ts.map +1 -1
  143. package/types/lib/helpers/utils.d.ts +45 -8
  144. package/types/lib/helpers/utils.d.ts.map +1 -1
  145. package/types/lib/managers/binary.d.ts +5 -0
  146. package/types/lib/managers/binary.d.ts.map +1 -1
  147. package/types/lib/managers/docker.d.ts.map +1 -1
  148. package/types/lib/server/server.d.ts +2 -1
  149. package/types/lib/server/server.d.ts.map +1 -1
  150. package/types/lib/stages/postgen/annotator.d.ts.map +1 -1
  151. package/types/lib/stages/postgen/auditBom.d.ts +26 -1
  152. package/types/lib/stages/postgen/auditBom.d.ts.map +1 -1
  153. package/types/lib/stages/postgen/postgen.d.ts +2 -1
  154. package/types/lib/stages/postgen/postgen.d.ts.map +1 -1
  155. package/types/lib/stages/postgen/ruleEngine.d.ts.map +1 -1
  156. package/types/lib/stages/pregen/envAudit.d.ts.map +1 -1
  157. package/data/spdx-model-v3.0.1.jsonld +0 -15999
@@ -7,6 +7,7 @@
7
7
  description: "Systemd units loaded from /tmp or /var/tmp can indicate unauthorized persistence."
8
8
  severity: high
9
9
  category: obom-runtime
10
+ dry-run-support: full
10
11
  condition: |
11
12
  components[
12
13
  $prop($, 'cdx:osquery:category') = 'systemd_units'
@@ -22,8 +23,8 @@
22
23
  "bomRef": $."bom-ref",
23
24
  "purl": purl
24
25
  }
25
- message: "Systemd unit '{{ name }}' references temporary execution artifacts in its unit file path configuration"
26
- mitigation: "Move unit files to trusted system paths, validate ownership/permissions, and re-enable only approved services."
26
+ message: "Systemd unit '{{ name }}' loads from unit path '{{ $firstNonEmpty($prop($, 'fragment_path'), $prop($, 'source_path'), name) }}' with temporary-backed source '{{ $firstNonEmpty($prop($, 'source_path'), $prop($, 'fragment_path')) }}'"
27
+ mitigation: "Review the unit file and any generated source/drop-in together, move them to trusted system paths, validate ownership/permissions, and re-enable only approved services."
27
28
  evidence: |
28
29
  {
29
30
  "activeState": $prop($, 'active_state'),
@@ -37,6 +38,7 @@
37
38
  description: "Sudoers entries allowing unrestricted command execution increase lateral movement and privilege escalation risk."
38
39
  severity: high
39
40
  category: obom-runtime
41
+ dry-run-support: full
40
42
  condition: |
41
43
  components[
42
44
  $prop($, 'cdx:osquery:category') = 'sudoers_snapshot'
@@ -63,6 +65,7 @@
63
65
  description: "Root SSH keys without command/from/no-agent-forwarding restrictions weaken access controls and traceability."
64
66
  severity: medium
65
67
  category: obom-runtime
68
+ dry-run-support: full
66
69
  condition: |
67
70
  components[
68
71
  $prop($, 'cdx:osquery:category') = 'authorized_keys_snapshot'
@@ -90,6 +93,7 @@
90
93
  description: "Drives with disabled BitLocker protection can violate endpoint encryption requirements and increase data exposure risk."
91
94
  severity: high
92
95
  category: obom-runtime
96
+ dry-run-support: full
93
97
  condition: |
94
98
  components[
95
99
  $prop($, 'cdx:osquery:category') = 'windows_bitlocker_info'
@@ -116,6 +120,7 @@
116
120
  description: "Poor Security Center health indicates one or more key endpoint protections are disabled or degraded."
117
121
  severity: high
118
122
  category: obom-runtime
123
+ dry-run-support: full
119
124
  condition: |
120
125
  components[
121
126
  $prop($, 'cdx:osquery:category') = 'windows_security_center'
@@ -150,6 +155,7 @@
150
155
  description: "Run/RunOnce entries launching from temp or encoded script commands are common persistence techniques."
151
156
  severity: critical
152
157
  category: obom-runtime
158
+ dry-run-support: full
153
159
  condition: |
154
160
  components[
155
161
  $prop($, 'cdx:osquery:category') = 'windows_run_keys'
@@ -179,6 +185,7 @@
179
185
  description: "ALF misconfiguration can expose endpoints to unsolicited inbound traffic and weakens host hardening baselines."
180
186
  severity: high
181
187
  category: obom-runtime
188
+ dry-run-support: full
182
189
  condition: |
183
190
  components[
184
191
  $prop($, 'cdx:osquery:category') = 'alf'
@@ -207,6 +214,7 @@
207
214
  description: "Launchd agents/daemons sourced from temporary paths are a strong persistence and execution abuse signal."
208
215
  severity: critical
209
216
  category: obom-runtime
217
+ dry-run-support: full
210
218
  condition: |
211
219
  components[
212
220
  $prop($, 'cdx:osquery:category') = 'launchd_services'
@@ -228,13 +236,15 @@
228
236
  "bomRef": $."bom-ref",
229
237
  "purl": purl
230
238
  }
231
- message: "Launchd entry '{{ name }}' executes from temporary path and is configured for persistence"
232
- mitigation: "Remove unauthorized plist entries, relocate approved binaries to trusted paths, and enforce signed launchd payloads."
239
+ message: "Launchd item '{{ $firstNonEmpty($prop($, 'label'), name) }}' uses plist '{{ $firstNonEmpty($prop($, 'path'), name) }}' and target '{{ $firstNonEmpty($prop($, 'program'), $prop($, 'program_arguments'), name) }}' from a temporary path with persistence enabled"
240
+ mitigation: "Review the launchd plist and target executable together, remove unauthorized entries, relocate approved binaries to trusted paths, and enforce signed launchd payloads."
233
241
  evidence: |
234
242
  {
235
243
  "label": $prop($, 'label'),
236
244
  "plistPath": $prop($, 'path'),
245
+ "targetPath": $firstNonEmpty($prop($, 'program'), $prop($, 'program_arguments')),
237
246
  "program": $prop($, 'program'),
247
+ "programArguments": $prop($, 'program_arguments'),
238
248
  "runAtLoad": $prop($, 'run_at_load'),
239
249
  "keepAlive": $prop($, 'keep_alive')
240
250
  }
@@ -244,6 +254,7 @@
244
254
  description: "ALF exceptions for binaries in user Downloads/Desktop/tmp increase risk of untrusted inbound network exposure."
245
255
  severity: medium
246
256
  category: obom-runtime
257
+ dry-run-support: full
247
258
  condition: |
248
259
  components[
249
260
  $prop($, 'cdx:osquery:category') = 'alf_exceptions'
@@ -274,6 +285,7 @@
274
285
  description: "Shell history with direct download-and-execute commands may indicate malware staging or hands-on-keyboard activity."
275
286
  severity: high
276
287
  category: obom-runtime
288
+ dry-run-support: full
277
289
  condition: |
278
290
  components[
279
291
  $prop($, 'cdx:osquery:category') = 'shell_history_snapshot'
@@ -304,6 +316,7 @@
304
316
  description: "Dockerd listening on TCP 2375 enables remote daemon control if not protected by network controls and TLS."
305
317
  severity: critical
306
318
  category: obom-runtime
319
+ dry-run-support: full
307
320
  condition: |
308
321
  components[
309
322
  $prop($, 'cdx:osquery:category') = 'listening_ports'
@@ -331,9 +344,10 @@
331
344
 
332
345
  - id: OBOM-LNX-006
333
346
  name: "Privileged Linux listener exposed on a non-local interface"
334
- description: "Root or service-account listeners bound to all interfaces expand attack surface and deserve proactive review."
335
- severity: high
347
+ description: "Root or service-account listeners bound to all interfaces expand attack surface and should be reviewed even when they appear to come from managed system paths."
348
+ severity: medium
336
349
  category: obom-runtime
350
+ dry-run-support: full
337
351
  condition: |
338
352
  components[
339
353
  $prop($, 'cdx:osquery:category') = 'privileged_listening_ports'
@@ -346,14 +360,21 @@
346
360
  and $safeStr(name) != 'systemd-resolved'
347
361
  and $safeStr(name) != 'avahi-daemon'
348
362
  and $safeStr(name) != 'cupsd'
363
+ and $safeStr($prop($, 'package_source_hint')) != 'user-writable-path'
364
+ and $safeStr($prop($, 'package_source_hint')) != 'unclassified-path'
365
+ and $not($contains($lowercase($nullSafeProp($, 'path')), '/tmp/'))
366
+ and $not($contains($lowercase($nullSafeProp($, 'path')), '/var/tmp/'))
367
+ and $not($contains($lowercase($nullSafeProp($, 'path')), '/dev/shm/'))
368
+ and $not($contains($lowercase($nullSafeProp($, 'path')), '/home/'))
369
+ and $not($contains($lowercase($nullSafeProp($, 'path')), '/run/user/'))
349
370
  ]
350
371
  location: |
351
372
  {
352
373
  "bomRef": $."bom-ref",
353
374
  "purl": purl
354
375
  }
355
- message: "Privileged listener '{{ name }}' is reachable on {{ $prop($, 'address') }}:{{ $prop($, 'port') }}"
356
- mitigation: "Restrict privileged services to local interfaces where possible, front them with authenticated proxies, and validate exposure against approved admin-surface inventory."
376
+ message: "Privileged listener '{{ name }}' from '{{ $firstNonEmpty($prop($, 'path'), name) }}' is reachable on {{ $prop($, 'address') }}:{{ $prop($, 'port') }} and should be validated against approved exposure"
377
+ mitigation: "Restrict privileged services to local interfaces where possible, front them with authenticated proxies, and validate the listener path and service ownership against approved admin-surface inventory."
357
378
  evidence: |
358
379
  {
359
380
  "account": $prop($, 'account'),
@@ -371,6 +392,7 @@
371
392
  description: "Cockpit, PackageKit, pkexec, and related admin surfaces running with elevated privileges should be continuously monitored for exposure and drift."
372
393
  severity: high
373
394
  category: obom-runtime
395
+ dry-run-support: full
374
396
  condition: |
375
397
  components[
376
398
  (
@@ -424,6 +446,7 @@
424
446
  description: "Interactive sudo or pkexec invocations against package-management and admin-control binaries can indicate privileged changes worth auditing."
425
447
  severity: high
426
448
  category: obom-runtime
449
+ dry-run-support: full
427
450
  condition: |
428
451
  components[
429
452
  $prop($, 'cdx:osquery:category') = 'sudo_executions'
@@ -476,6 +499,7 @@
476
499
  description: "Setuid/setgid transitions outside a small baseline of expected tools can indicate risky privilege-bound packages or exploit activity."
477
500
  severity: high
478
501
  category: obom-runtime
502
+ dry-run-support: full
479
503
  condition: |
480
504
  components[
481
505
  $prop($, 'cdx:osquery:category') = 'privilege_transitions'
@@ -519,10 +543,11 @@
519
543
  }
520
544
 
521
545
  - id: OBOM-LNX-010
522
- name: "Elevated Linux process launched from user-writable or unusual path"
523
- description: "Root processes executing from user-controlled or non-standard paths are a strong signal for persistence or package drift."
546
+ name: "Elevated Linux process launched from user-writable or temporary path"
547
+ description: "Root processes executing from explicit user-controlled, temporary, or per-user runtime paths are a strong signal for persistence or package drift."
524
548
  severity: critical
525
549
  category: obom-runtime
550
+ dry-run-support: full
526
551
  condition: |
527
552
  components[
528
553
  $prop($, 'cdx:osquery:category') = 'elevated_processes'
@@ -533,8 +558,12 @@
533
558
  or $contains($nullSafeProp($, 'path'), '/dev/shm/')
534
559
  or $contains($nullSafeProp($, 'path'), '/home/')
535
560
  or $contains($nullSafeProp($, 'path'), '/run/user/')
561
+ or $contains($nullSafeProp($, 'cmdline'), '/tmp/')
562
+ or $contains($nullSafeProp($, 'cmdline'), '/var/tmp/')
563
+ or $contains($nullSafeProp($, 'cmdline'), '/dev/shm/')
564
+ or $contains($nullSafeProp($, 'cmdline'), '/home/')
565
+ or $contains($nullSafeProp($, 'cmdline'), '/run/user/')
536
566
  or $safeStr($prop($, 'package_source_hint')) = 'user-writable-path'
537
- or $safeStr($prop($, 'package_source_hint')) = 'unclassified-path'
538
567
  )
539
568
  and $safeStr(name) != 'systemd'
540
569
  and $safeStr(name) != 'init'
@@ -544,12 +573,13 @@
544
573
  "bomRef": $."bom-ref",
545
574
  "purl": purl
546
575
  }
547
- message: "Elevated process '{{ name }}' executes from a risky path: {{ $prop($, 'path') }}"
548
- mitigation: "Move approved binaries into trusted system locations, validate package ownership, and investigate any root process sourced from writable directories."
576
+ message: "Elevated process '{{ name }}' executes from a risky path or command: {{ $firstNonEmpty($prop($, 'path'), $prop($, 'cmdline'), name) }}"
577
+ mitigation: "Validate the executable path and full command line, move approved binaries into trusted system locations, and investigate any root process sourced from writable directories or per-user runtime paths."
549
578
  evidence: |
550
579
  {
551
580
  "account": $prop($, 'account'),
552
581
  "path": $prop($, 'path'),
582
+ "cmdline": $prop($, 'cmdline'),
553
583
  "serviceUnit": $prop($, 'service_unit'),
554
584
  "parentPath": $prop($, 'parent_path'),
555
585
  "parentCmdline": $prop($, 'parent_cmdline'),
@@ -562,6 +592,7 @@
562
592
  description: "Shell-driven privileged chains are useful for separating admin changes from long-running service behavior."
563
593
  severity: medium
564
594
  category: obom-runtime
595
+ dry-run-support: full
565
596
  condition: |
566
597
  components[
567
598
  $prop($, 'cdx:osquery:category') = 'sudo_executions'
@@ -599,11 +630,68 @@
599
630
  "timestamp": $prop($, 'time')
600
631
  }
601
632
 
633
+ - id: OBOM-LNX-012
634
+ name: "Linux Secure Boot inventory contains revoked certificate"
635
+ description: "Revoked entries in the Secure Boot trust inventory can indicate stale firmware trust policy or unexpected dbx posture drift."
636
+ severity: high
637
+ category: obom-runtime
638
+ dry-run-support: full
639
+ condition: |
640
+ components[
641
+ $prop($, 'cdx:osquery:category') = 'secureboot_certificates'
642
+ and $safeStr($prop($, 'revoked')) = '1'
643
+ ]
644
+ location: |
645
+ {
646
+ "bomRef": $."bom-ref",
647
+ "purl": purl
648
+ }
649
+ message: "Secure Boot certificate '{{ name }}' is marked revoked in firmware trust inventory"
650
+ mitigation: "Review db/dbx enrollment, remove stale trust anchors, and reconcile firmware policy with approved platform signing certificates."
651
+ evidence: |
652
+ {
653
+ "subject": $prop($, 'subject'),
654
+ "issuer": $prop($, 'issuer'),
655
+ "serial": $prop($, 'serial'),
656
+ "path": $prop($, 'path'),
657
+ "notValidAfter": $prop($, 'not_valid_after')
658
+ }
659
+
660
+ - id: OBOM-LNX-013
661
+ name: "Linux Secure Boot certificate expired or expiring soon"
662
+ description: "Secure Boot trust anchors nearing expiry can cause firmware validation drift and interrupt planned key rotation windows."
663
+ severity: medium
664
+ category: obom-runtime
665
+ dry-run-support: full
666
+ condition: |
667
+ components[
668
+ $prop($, 'cdx:osquery:category') = 'secureboot_certificates'
669
+ and $safeStr($prop($, 'not_valid_after')) != ''
670
+ and $number($prop($, 'not_valid_after')) <= ($floor($millis() / 1000) + 2592000)
671
+ ]
672
+ location: |
673
+ {
674
+ "bomRef": $."bom-ref",
675
+ "purl": purl
676
+ }
677
+ message: "Secure Boot certificate '{{ name }}' expires at {{ $prop($, 'not_valid_after') }} and should be rotated or reviewed"
678
+ mitigation: "Rotate or re-enroll Secure Boot certificates before expiry and validate firmware trust stores against your approved signing hierarchy."
679
+ evidence: |
680
+ {
681
+ "subject": $prop($, 'subject'),
682
+ "issuer": $prop($, 'issuer'),
683
+ "serial": $prop($, 'serial'),
684
+ "path": $prop($, 'path'),
685
+ "notValidBefore": $prop($, 'not_valid_before'),
686
+ "notValidAfter": $prop($, 'not_valid_after')
687
+ }
688
+
602
689
  - id: OBOM-WIN-004
603
690
  name: "Hidden scheduled task uses suspicious execution path"
604
691
  description: "Enabled hidden tasks executing from temp paths or encoded script launchers are common persistence tradecraft."
605
692
  severity: high
606
693
  category: obom-runtime
694
+ dry-run-support: full
607
695
  condition: |
608
696
  components[
609
697
  $prop($, 'cdx:osquery:category') = 'scheduled_tasks'
@@ -634,6 +722,7 @@
634
722
  description: "Auto-start services from temp or AppData paths may indicate privilege persistence through service hijacking."
635
723
  severity: critical
636
724
  category: obom-runtime
725
+ dry-run-support: full
637
726
  condition: |
638
727
  components[
639
728
  $prop($, 'cdx:osquery:category') = 'services_snapshot'
@@ -659,10 +748,11 @@
659
748
  }
660
749
 
661
750
  - id: OBOM-WIN-006
662
- name: "Windows persistence surface references LOLBAS execution helper"
663
- description: "Run keys, startup items, scheduled tasks, or auto-start services that reference LOLBAS execution helpers deserve elevated review because they blend persistence with proxy execution tradecraft."
751
+ name: "Windows suspicious persistence surface references LOLBAS execution helper"
752
+ description: "Any Windows persistence or startup surface that invokes a LOLBAS helper deserves review, including vendor- or platform-managed maintenance registrations, because these surfaces can become breachable execution targets."
664
753
  severity: high
665
754
  category: obom-runtime
755
+ dry-run-support: full
666
756
  condition: |
667
757
  components[
668
758
  $prop($, 'cdx:lolbas:matched') = 'true'
@@ -685,14 +775,16 @@
685
775
  "bomRef": $."bom-ref",
686
776
  "purl": purl
687
777
  }
688
- message: "Windows persistence surface '{{ name }}' references LOLBAS helper(s) {{ $prop($, 'cdx:lolbas:names') }}"
689
- mitigation: "Validate the owning change, replace proxy-execution helpers with signed managed binaries where possible, and baseline approved startup surfaces with allowlists."
778
+ message: "Windows {{ $prop($, 'cdx:osquery:category') }} registration '{{ $firstNonEmpty($prop($, 'key'), $prop($, 'path'), name) }}' launches '{{ $firstNonEmpty($prop($, 'action'), $prop($, 'executable'), $prop($, 'module_path'), $prop($, 'path'), description, name) }}' via LOLBAS helper(s) {{ $prop($, 'cdx:lolbas:names') }}"
779
+ mitigation: "Review the registration surface and launched command together, validate the owning change, and do not auto-trust managed or vendor-owned maintenance surfaces without provenance and hardening review."
690
780
  attack:
691
- tactics: [TA0003, TA0005]
781
+ tactics: [TA0003, TA0004, TA0005]
692
782
  techniques: [T1218, T1547]
693
783
  evidence: |
694
784
  {
695
785
  "queryCategory": $prop($, 'cdx:osquery:category'),
786
+ "registrationPath": $firstNonEmpty($prop($, 'key'), $prop($, 'path'), name),
787
+ "targetPath": $firstNonEmpty($prop($, 'action'), $prop($, 'executable'), $prop($, 'module_path'), $prop($, 'path'), description),
696
788
  "lolbasNames": $prop($, 'cdx:lolbas:names'),
697
789
  "functions": $prop($, 'cdx:lolbas:functions'),
698
790
  "matchFields": $prop($, 'cdx:lolbas:matchFields'),
@@ -706,6 +798,7 @@
706
798
  description: "WMI command consumers and AppCompat shims that invoke LOLBAS utilities are high-signal persistence and defense-evasion indicators."
707
799
  severity: critical
708
800
  category: obom-runtime
801
+ dry-run-support: full
709
802
  condition: |
710
803
  components[
711
804
  $prop($, 'cdx:lolbas:matched') = 'true'
@@ -723,7 +816,7 @@
723
816
  message: "WMI/AppCompat persistence artifact '{{ name }}' references LOLBAS helper(s) {{ $prop($, 'cdx:lolbas:names') }}"
724
817
  mitigation: "Treat as a persistence investigation, review WMI repository and shim databases, and remove unauthorized subscriptions or shim registrations."
725
818
  attack:
726
- tactics: [TA0003, TA0005]
819
+ tactics: [TA0003, TA0004, TA0005]
727
820
  techniques: [T1218, T1546]
728
821
  evidence: |
729
822
  {
@@ -742,6 +835,7 @@
742
835
  description: "Network-capable LOLBAS helpers such as PowerShell, Certutil, Bitsadmin, or WMIC become higher priority when they appear in persistence surfaces or suspicious live process command lines."
743
836
  severity: high
744
837
  category: obom-runtime
838
+ dry-run-support: full
745
839
  condition: |
746
840
  components[
747
841
  $prop($, 'cdx:lolbas:matched') = 'true'
@@ -771,7 +865,7 @@
771
865
  message: "Network-capable LOLBAS helper(s) {{ $prop($, 'cdx:lolbas:names') }} detected in '{{ $prop($, 'cdx:osquery:category') }}'"
772
866
  mitigation: "Correlate with outbound connections and downloads, restrict unmanaged scripting/network utilities, and investigate encoded or remote-fetch command lines."
773
867
  attack:
774
- tactics: [TA0002, TA0011]
868
+ tactics: [TA0002, TA0010, TA0011]
775
869
  techniques: [T1041, T1059.001, T1105]
776
870
  evidence: |
777
871
  {
@@ -788,6 +882,7 @@
788
882
  description: "A listening process backed by a LOLBAS execution helper is a strong remote-control or staging indicator on Windows endpoints."
789
883
  severity: critical
790
884
  category: obom-runtime
885
+ dry-run-support: full
791
886
  condition: |
792
887
  components[
793
888
  $prop($, 'cdx:osquery:category') = 'listening_ports'
@@ -810,7 +905,7 @@
810
905
  message: "Listening process '{{ name }}' on {{ $prop($, 'address') }}:{{ $prop($, 'port') }} matches LOLBAS helper(s) {{ $prop($, 'cdx:lolbas:names') }}"
811
906
  mitigation: "Review parent process lineage, isolate unmanaged listeners, and block or remove unexpected inbound admin or scripting surfaces."
812
907
  attack:
813
- tactics: [TA0008, TA0011]
908
+ tactics: [TA0002, TA0005, TA0011]
814
909
  techniques: [T1059, T1105, T1218]
815
910
  evidence: |
816
911
  {
@@ -827,6 +922,7 @@
827
922
  description: "Persistence surfaces that reference LOLBAS helpers documented with UAC-bypass behavior should be treated as privilege-escalation investigations."
828
923
  severity: critical
829
924
  category: obom-runtime
925
+ dry-run-support: full
830
926
  condition: |
831
927
  components[
832
928
  $prop($, 'cdx:lolbas:matched') = 'true'
@@ -847,7 +943,7 @@
847
943
  message: "UAC-bypass-capable LOLBAS helper(s) {{ $prop($, 'cdx:lolbas:names') }} detected in Windows persistence artifact '{{ name }}'"
848
944
  mitigation: "Investigate as a possible privilege-escalation foothold, remove unauthorized registration points, and enforce WDAC/AppLocker policies for known proxy binaries."
849
945
  attack:
850
- tactics: [TA0003, TA0004, TA0005]
946
+ tactics: [TA0004, TA0005]
851
947
  techniques: [T1548.002, T1218]
852
948
  evidence: |
853
949
  {
@@ -864,6 +960,7 @@
864
960
  description: "Launchd overrides disabling Apple-managed services can indicate tampering with built-in security or platform controls."
865
961
  severity: medium
866
962
  category: obom-runtime
963
+ dry-run-support: full
867
964
  condition: |
868
965
  components[
869
966
  $prop($, 'cdx:osquery:category') = 'launchd_overrides'
@@ -889,3 +986,791 @@
889
986
  "uid": $prop($, 'uid'),
890
987
  "plistPath": $prop($, 'path')
891
988
  }
989
+
990
+ - id: OBOM-MAC-005
991
+ name: "macOS Gatekeeper enforcement is disabled or weakened"
992
+ description: "Gatekeeper should enforce assessments and identified-developer checks on managed macOS endpoints."
993
+ severity: high
994
+ category: obom-runtime
995
+ dry-run-support: full
996
+ condition: |
997
+ components[
998
+ $prop($, 'cdx:osquery:category') = 'gatekeeper'
999
+ and (
1000
+ $safeStr($prop($, 'assessments_enabled')) != '1'
1001
+ or $safeStr($prop($, 'dev_id_enabled')) != '1'
1002
+ )
1003
+ ]
1004
+ location: |
1005
+ {
1006
+ "bomRef": $."bom-ref",
1007
+ "purl": purl
1008
+ }
1009
+ message: "Gatekeeper posture is weakened (assessments_enabled={{ $prop($, 'assessments_enabled') }}, dev_id_enabled={{ $prop($, 'dev_id_enabled') }})"
1010
+ mitigation: "Re-enable Gatekeeper assessments and identified-developer enforcement with spctl or an MDM configuration profile, then validate the host against baseline policy."
1011
+ evidence: |
1012
+ {
1013
+ "gatekeeperVersion": version,
1014
+ "opaqueVersion": description,
1015
+ "assessmentsEnabled": $prop($, 'assessments_enabled'),
1016
+ "devIdEnabled": $prop($, 'dev_id_enabled')
1017
+ }
1018
+
1019
+ - id: OBOM-LNX-014
1020
+ name: "Linux reverse shell behavior detected in live process telemetry"
1021
+ description: "A shell process with a live remote socket is a strong signal for hands-on-keyboard abuse, staging, or remote command execution."
1022
+ severity: critical
1023
+ category: obom-runtime
1024
+ dry-run-support: full
1025
+ condition: |
1026
+ components[
1027
+ $prop($, 'cdx:osquery:category') = 'behavioral_reverse_shell'
1028
+ ]
1029
+ location: |
1030
+ {
1031
+ "bomRef": $."bom-ref",
1032
+ "purl": purl
1033
+ }
1034
+ message: "Reverse-shell-like process behavior detected for '{{ name }}' reaching {{ $prop($, 'remote_address') }}:{{ $prop($, 'remote_port') }}"
1035
+ mitigation: "Isolate the host, review process lineage and parent shell context, and confirm whether the remote session is expected administrative activity."
1036
+ evidence: |
1037
+ {
1038
+ "path": $prop($, 'path'),
1039
+ "cmdline": $prop($, 'cmdline'),
1040
+ "parentCmdline": $prop($, 'parent_cmdline'),
1041
+ "remoteAddress": $prop($, 'remote_address'),
1042
+ "remotePort": $prop($, 'remote_port')
1043
+ }
1044
+
1045
+ - id: OBOM-LNX-015
1046
+ name: "Linux process uses LD_PRELOAD from writable or temporary path"
1047
+ description: "LD_PRELOAD pointing at user-controlled paths can indicate library hijacking, stealth persistence, or runtime tampering."
1048
+ severity: high
1049
+ category: obom-runtime
1050
+ dry-run-support: full
1051
+ condition: |
1052
+ components[
1053
+ $prop($, 'cdx:osquery:category') = 'ld_preload'
1054
+ and (
1055
+ $contains($lowercase($safeStr($prop($, 'value'))), '/tmp/')
1056
+ or $contains($lowercase($safeStr($prop($, 'value'))), '/var/tmp/')
1057
+ or $contains($lowercase($safeStr($prop($, 'value'))), '/dev/shm/')
1058
+ or $contains($lowercase($safeStr($prop($, 'value'))), '/home/')
1059
+ or $contains($lowercase($safeStr($prop($, 'value'))), '/run/user/')
1060
+ )
1061
+ ]
1062
+ location: |
1063
+ {
1064
+ "bomRef": $."bom-ref",
1065
+ "purl": purl
1066
+ }
1067
+ message: "Process '{{ name }}' sets LD_PRELOAD to a risky path: {{ $prop($, 'value') }}"
1068
+ mitigation: "Review the preload library, remove unauthorized runtime injection, and compare the process with package ownership and startup history."
1069
+ evidence: |
1070
+ {
1071
+ "processPath": $prop($, 'path'),
1072
+ "cmdline": $prop($, 'cmdline'),
1073
+ "cwd": $prop($, 'cwd'),
1074
+ "ldPreload": $prop($, 'value')
1075
+ }
1076
+
1077
+ - id: OBOM-LNX-016
1078
+ name: "Linux cron entry fetches remote content or runs from writable path"
1079
+ description: "Cron jobs that fetch remote content or execute from temporary and user-writable paths are a high-signal persistence pattern."
1080
+ severity: high
1081
+ category: obom-runtime
1082
+ dry-run-support: full
1083
+ condition: |
1084
+ components[
1085
+ $prop($, 'cdx:osquery:category') = 'crontab_snapshot'
1086
+ and (
1087
+ (
1088
+ (
1089
+ $contains($lowercase($safeStr($prop($, 'command'))), 'curl ')
1090
+ or $contains($lowercase($safeStr($prop($, 'command'))), 'wget ')
1091
+ )
1092
+ and (
1093
+ $contains($lowercase($safeStr($prop($, 'command'))), 'http://')
1094
+ or $contains($lowercase($safeStr($prop($, 'command'))), 'https://')
1095
+ or $contains($lowercase($safeStr($prop($, 'command'))), '| sh')
1096
+ or $contains($lowercase($safeStr($prop($, 'command'))), '| bash')
1097
+ )
1098
+ )
1099
+ or $contains($lowercase($safeStr($prop($, 'command'))), '/tmp/')
1100
+ or $contains($lowercase($safeStr($prop($, 'command'))), '/var/tmp/')
1101
+ or $contains($lowercase($safeStr($prop($, 'command'))), '/dev/shm/')
1102
+ or $contains($lowercase($safeStr($prop($, 'command'))), '/home/')
1103
+ )
1104
+ ]
1105
+ location: |
1106
+ {
1107
+ "bomRef": $."bom-ref",
1108
+ "purl": purl
1109
+ }
1110
+ message: "Cron entry '{{ name }}' has a risky command: {{ $prop($, 'command') }}"
1111
+ mitigation: "Move bootstrap downloads into a managed deployment path, review cron ownership, and remove unauthorized recurring tasks."
1112
+ evidence: |
1113
+ {
1114
+ "command": $prop($, 'command'),
1115
+ "path": $prop($, 'path'),
1116
+ "minute": $prop($, 'minute'),
1117
+ "hour": $prop($, 'hour')
1118
+ }
1119
+
1120
+ - id: OBOM-LNX-017
1121
+ name: "Linux sysctl posture diverges from common hardening baseline"
1122
+ description: "Weak ASLR and redirect-handling sysctl values are commonly called out in Lynis and CIS-style hardening reviews."
1123
+ severity: medium
1124
+ category: obom-runtime
1125
+ dry-run-support: full
1126
+ condition: |
1127
+ components[
1128
+ $prop($, 'cdx:osquery:category') = 'sysctl_hardening'
1129
+ and (
1130
+ (name = 'kernel.randomize_va_space' and $safeStr(version) != '2')
1131
+ or (name = 'kernel.kptr_restrict' and $safeStr(version) = '0')
1132
+ or (
1133
+ (
1134
+ name = 'net.ipv4.conf.all.accept_redirects'
1135
+ or name = 'net.ipv4.conf.default.accept_redirects'
1136
+ or name = 'net.ipv4.conf.all.send_redirects'
1137
+ or name = 'net.ipv4.conf.default.send_redirects'
1138
+ )
1139
+ and $safeStr(version) = '1'
1140
+ )
1141
+ )
1142
+ ]
1143
+ location: |
1144
+ {
1145
+ "bomRef": $."bom-ref",
1146
+ "purl": purl
1147
+ }
1148
+ message: "Sysctl '{{ name }}' has a weak hardening value: {{ version }}"
1149
+ mitigation: "Align the sysctl value with your baseline, apply the setting persistently, and validate whether the deviation is truly required for this host."
1150
+ evidence: |
1151
+ {
1152
+ "sysctl": name,
1153
+ "value": version
1154
+ }
1155
+
1156
+ - id: OBOM-LNX-018
1157
+ name: "Linux temporary mount is missing key hardening flags"
1158
+ description: "Temporary and shared-memory mounts should usually carry noexec, nosuid, and nodev protections on hardened hosts."
1159
+ severity: high
1160
+ category: obom-runtime
1161
+ dry-run-support: full
1162
+ condition: |
1163
+ components[
1164
+ $prop($, 'cdx:osquery:category') = 'mount_hardening'
1165
+ and (
1166
+ name = '/tmp'
1167
+ or name = '/var/tmp'
1168
+ or name = '/dev/shm'
1169
+ )
1170
+ and (
1171
+ $not($contains($lowercase($safeStr(version)), 'noexec'))
1172
+ or $not($contains($lowercase($safeStr(version)), 'nosuid'))
1173
+ or $not($contains($lowercase($safeStr(version)), 'nodev'))
1174
+ )
1175
+ ]
1176
+ location: |
1177
+ {
1178
+ "bomRef": $."bom-ref",
1179
+ "purl": purl
1180
+ }
1181
+ message: "Mount '{{ name }}' is missing one or more hardening flags: {{ version }}"
1182
+ mitigation: "Review whether the mount should carry noexec, nosuid, and nodev, then enforce the chosen baseline through fstab, systemd mounts, or image build policy."
1183
+ evidence: |
1184
+ {
1185
+ "mount": name,
1186
+ "flags": version,
1187
+ "device": description,
1188
+ "type": $prop($, 'type')
1189
+ }
1190
+
1191
+ - id: OBOM-LNX-019
1192
+ name: "Live Linux runtime artifact matches GTFOBins execution helper"
1193
+ description: "GTFOBins-capable binaries in privileged or network-active runtime contexts deserve elevated review because they compress execution, persistence, and lateral movement tradecraft into familiar tools."
1194
+ severity: high
1195
+ category: obom-runtime
1196
+ dry-run-support: full
1197
+ condition: |
1198
+ components[
1199
+ $prop($, 'cdx:gtfobins:matched') = 'true'
1200
+ and (
1201
+ $prop($, 'cdx:osquery:category') = 'sudo_executions'
1202
+ or $prop($, 'cdx:osquery:category') = 'privilege_transitions'
1203
+ or $prop($, 'cdx:osquery:category') = 'privileged_listening_ports'
1204
+ or $prop($, 'cdx:osquery:category') = 'behavioral_reverse_shell'
1205
+ or (
1206
+ $prop($, 'cdx:osquery:category') = 'elevated_processes'
1207
+ and (
1208
+ $safeStr($prop($, 'package_source_hint')) = 'user-writable-path'
1209
+ or $contains($nullSafeProp($, 'path'), '/tmp/')
1210
+ or $contains($nullSafeProp($, 'path'), '/var/tmp/')
1211
+ or $contains($nullSafeProp($, 'path'), '/dev/shm/')
1212
+ or $contains($nullSafeProp($, 'path'), '/home/')
1213
+ or $contains($nullSafeProp($, 'path'), '/run/user/')
1214
+ or $contains($nullSafeProp($, 'cmdline'), '/tmp/')
1215
+ or $contains($nullSafeProp($, 'cmdline'), '/var/tmp/')
1216
+ or $contains($nullSafeProp($, 'cmdline'), '/dev/shm/')
1217
+ or $contains($nullSafeProp($, 'cmdline'), '/home/')
1218
+ or $contains($nullSafeProp($, 'cmdline'), '/run/user/')
1219
+ )
1220
+ )
1221
+ )
1222
+ and (
1223
+ $listContains($prop($, 'cdx:gtfobins:functions'), 'shell')
1224
+ or $listContains($prop($, 'cdx:gtfobins:functions'), 'command')
1225
+ or $listContains($prop($, 'cdx:gtfobins:functions'), 'reverse-shell')
1226
+ )
1227
+ ]
1228
+ location: |
1229
+ {
1230
+ "bomRef": $."bom-ref",
1231
+ "purl": purl
1232
+ }
1233
+ message: "Runtime artifact '{{ name }}' matches GTFOBins helper(s) {{ $prop($, 'cdx:gtfobins:names') }} in '{{ $prop($, 'cdx:osquery:category') }}'"
1234
+ mitigation: "Validate the binary provenance and operator intent, then review related sudo, privilege-transition, listener, and remote-connection telemetry before suppressing the finding."
1235
+ evidence: |
1236
+ {
1237
+ "queryCategory": $prop($, 'cdx:osquery:category'),
1238
+ "gtfobinsNames": $prop($, 'cdx:gtfobins:names'),
1239
+ "functions": $prop($, 'cdx:gtfobins:functions'),
1240
+ "contexts": $prop($, 'cdx:gtfobins:contexts'),
1241
+ "riskTags": $prop($, 'cdx:gtfobins:riskTags'),
1242
+ "path": $prop($, 'path'),
1243
+ "cmdline": $prop($, 'cmdline')
1244
+ }
1245
+
1246
+ - id: OBOM-WIN-011
1247
+ name: "Windows Public profile inbound firewall allow rule"
1248
+ description: "Inbound allow rules on the Public firewall profile can expose services beyond expected trust boundaries."
1249
+ severity: high
1250
+ category: obom-runtime
1251
+ dry-run-support: full
1252
+ condition: |
1253
+ components[
1254
+ $prop($, 'cdx:osquery:category') = 'windows_firewall_rules'
1255
+ and (
1256
+ $lowercase($safeStr($prop($, 'enabled'))) = '1'
1257
+ or $lowercase($safeStr($prop($, 'enabled'))) = 'true'
1258
+ )
1259
+ and $lowercase($safeStr($prop($, 'direction'))) = 'in'
1260
+ and $lowercase($safeStr($prop($, 'action'))) = 'allow'
1261
+ and $contains($lowercase($safeStr($prop($, 'profile'))), 'public')
1262
+ ]
1263
+ location: |
1264
+ {
1265
+ "bomRef": $."bom-ref",
1266
+ "purl": purl
1267
+ }
1268
+ message: "Firewall rule '{{ name }}' allows inbound traffic on the Public profile"
1269
+ mitigation: "Narrow the rule scope, move it to a more trusted profile when justified, and verify the backing service really needs public-network reachability."
1270
+ evidence: |
1271
+ {
1272
+ "action": $prop($, 'action'),
1273
+ "direction": $prop($, 'direction'),
1274
+ "profile": $prop($, 'profile'),
1275
+ "localPorts": $prop($, 'local_ports'),
1276
+ "remoteAddresses": $prop($, 'remote_addresses')
1277
+ }
1278
+
1279
+ - id: OBOM-WIN-012
1280
+ name: "Windows startup or listener binary has invalid Authenticode status"
1281
+ description: "Persistence and network-facing artifacts backed by definitively invalid Authenticode status deserve urgent review on managed Windows hosts."
1282
+ severity: critical
1283
+ category: obom-runtime
1284
+ dry-run-support: full
1285
+ condition: |
1286
+ components[
1287
+ (
1288
+ $prop($, 'cdx:osquery:category') = 'windows_run_keys'
1289
+ or $prop($, 'cdx:osquery:category') = 'scheduled_tasks'
1290
+ or $prop($, 'cdx:osquery:category') = 'startup_items'
1291
+ or $prop($, 'cdx:osquery:category') = 'services_snapshot'
1292
+ or $prop($, 'cdx:osquery:category') = 'listening_ports'
1293
+ )
1294
+ and $not(
1295
+ $contains(
1296
+ $lowercase(
1297
+ $firstNonEmpty(
1298
+ $prop($, 'image_path'),
1299
+ $prop($, 'executable'),
1300
+ $prop($, 'action'),
1301
+ $prop($, 'module_path'),
1302
+ $prop($, 'path'),
1303
+ description,
1304
+ name
1305
+ )
1306
+ ),
1307
+ '.lnk'
1308
+ )
1309
+ )
1310
+ and $hasProp($, 'cdx:windows:authenticode:status')
1311
+ and $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) != 'valid'
1312
+ and $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) != 'unknown'
1313
+ and $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) != 'unknownerror'
1314
+ and $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) != 'unknown_error'
1315
+ ]
1316
+ location: |
1317
+ {
1318
+ "bomRef": $."bom-ref",
1319
+ "purl": purl
1320
+ }
1321
+ message: "Windows {{ $prop($, 'cdx:osquery:category') }} registration '{{ $firstNonEmpty($prop($, 'key'), $prop($, 'path'), name) }}' resolves to '{{ $firstNonEmpty($prop($, 'image_path'), $prop($, 'executable'), $prop($, 'action'), $prop($, 'module_path'), $prop($, 'path'), description, name) }}' with Authenticode status {{ $prop($, 'cdx:windows:authenticode:status') }}"
1322
+ mitigation: "Review the startup/listener registration and backing binary together, treat the executable as suspicious until provenance is confirmed, compare the hash and signer with an approved baseline, and investigate who registered the surface."
1323
+ evidence: |
1324
+ {
1325
+ "queryCategory": $prop($, 'cdx:osquery:category'),
1326
+ "registrationPath": $firstNonEmpty($prop($, 'key'), $prop($, 'path'), name),
1327
+ "targetPath": $firstNonEmpty($prop($, 'image_path'), $prop($, 'executable'), $prop($, 'action'), $prop($, 'module_path'), $prop($, 'path'), description),
1328
+ "path": $prop($, 'path'),
1329
+ "imagePath": $prop($, 'image_path'),
1330
+ "action": $prop($, 'action'),
1331
+ "authenticodeStatus": $prop($, 'cdx:windows:authenticode:status'),
1332
+ "signerSubject": $prop($, 'cdx:windows:authenticode:signerSubject')
1333
+ }
1334
+
1335
+ - id: OBOM-WIN-014
1336
+ name: "Windows user-controlled startup or listener binary has unresolved Authenticode status"
1337
+ description: "Unknown Authenticode state on binaries launched from user-controlled startup or network-facing surfaces deserves review even when Windows cannot conclusively mark the signature invalid."
1338
+ severity: high
1339
+ category: obom-runtime
1340
+ dry-run-support: full
1341
+ condition: |
1342
+ components[
1343
+ (
1344
+ $prop($, 'cdx:osquery:category') = 'windows_run_keys'
1345
+ or $prop($, 'cdx:osquery:category') = 'scheduled_tasks'
1346
+ or $prop($, 'cdx:osquery:category') = 'startup_items'
1347
+ or $prop($, 'cdx:osquery:category') = 'services_snapshot'
1348
+ or $prop($, 'cdx:osquery:category') = 'listening_ports'
1349
+ )
1350
+ and $not(
1351
+ $contains(
1352
+ $lowercase(
1353
+ $firstNonEmpty(
1354
+ $prop($, 'image_path'),
1355
+ $prop($, 'executable'),
1356
+ $prop($, 'action'),
1357
+ $prop($, 'module_path'),
1358
+ $prop($, 'path'),
1359
+ description,
1360
+ name
1361
+ )
1362
+ ),
1363
+ '.lnk'
1364
+ )
1365
+ )
1366
+ and $hasProp($, 'cdx:windows:authenticode:status')
1367
+ and (
1368
+ $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) = 'unknown'
1369
+ or $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) = 'unknownerror'
1370
+ or $lowercase($safeStr($prop($, 'cdx:windows:authenticode:status'))) = 'unknown_error'
1371
+ )
1372
+ and (
1373
+ $isWindowsUserControlledPath(
1374
+ $firstNonEmpty(
1375
+ $prop($, 'image_path'),
1376
+ $prop($, 'executable'),
1377
+ $prop($, 'action'),
1378
+ description,
1379
+ $prop($, 'path'),
1380
+ name
1381
+ )
1382
+ )
1383
+ or $isWindowsUserControlledPath(
1384
+ $firstNonEmpty($prop($, 'path'), $prop($, 'key'), name)
1385
+ )
1386
+ )
1387
+ ]
1388
+ location: |
1389
+ {
1390
+ "bomRef": $."bom-ref",
1391
+ "purl": purl
1392
+ }
1393
+ message: "Windows {{ $prop($, 'cdx:osquery:category') }} registration '{{ $firstNonEmpty($prop($, 'key'), $prop($, 'path'), name) }}' resolves to '{{ $firstNonEmpty($prop($, 'image_path'), $prop($, 'executable'), $prop($, 'action'), $prop($, 'module_path'), $prop($, 'path'), description, name) }}' with unresolved Authenticode status {{ $prop($, 'cdx:windows:authenticode:status') }}"
1394
+ mitigation: "Review the startup/listener registration and backing binary together, confirm signature collection completed successfully, compare the hash and signer with an approved baseline, and prioritize cleanup of user-controlled execution paths."
1395
+ evidence: |
1396
+ {
1397
+ "queryCategory": $prop($, 'cdx:osquery:category'),
1398
+ "registrationPath": $firstNonEmpty($prop($, 'key'), $prop($, 'path'), name),
1399
+ "targetPath": $firstNonEmpty($prop($, 'image_path'), $prop($, 'executable'), $prop($, 'action'), $prop($, 'module_path'), $prop($, 'path'), description),
1400
+ "path": $prop($, 'path'),
1401
+ "imagePath": $prop($, 'image_path'),
1402
+ "action": $prop($, 'action'),
1403
+ "authenticodeStatus": $prop($, 'cdx:windows:authenticode:status'),
1404
+ "signerSubject": $prop($, 'cdx:windows:authenticode:signerSubject')
1405
+ }
1406
+
1407
+ - id: OBOM-WIN-013
1408
+ name: "Windows host has no active WDAC policies"
1409
+ description: "A managed Windows endpoint with no active WDAC policy loses an important application control and allowlisting layer."
1410
+ severity: high
1411
+ category: obom-runtime
1412
+ dry-run-support: full
1413
+ condition: |
1414
+ components[
1415
+ $hasProp($, 'cdx:windows:wdac:activePolicyCount')
1416
+ and $safeStr($prop($, 'cdx:windows:wdac:activePolicyCount')) = '0'
1417
+ ]
1418
+ location: |
1419
+ {
1420
+ "bomRef": $."bom-ref",
1421
+ "purl": purl
1422
+ }
1423
+ message: "Windows Defender Application Control is not enforcing any active policy on this host"
1424
+ mitigation: "Deploy or restore the approved WDAC policy set and review why policy enforcement is absent on the endpoint."
1425
+ evidence: |
1426
+ {
1427
+ "component": name,
1428
+ "activePolicyCount": $prop($, 'cdx:windows:wdac:activePolicyCount')
1429
+ }
1430
+
1431
+ - id: OBOM-MAC-006
1432
+ name: "macOS running app launches from Downloads, Desktop, or temporary path"
1433
+ description: "User-space execution from Downloads, Desktop, or temporary folders is a useful triage signal for ad hoc tooling and unreviewed payloads."
1434
+ severity: medium
1435
+ category: obom-runtime
1436
+ dry-run-support: full
1437
+ condition: |
1438
+ components[
1439
+ $prop($, 'cdx:osquery:category') = 'running_apps'
1440
+ and (
1441
+ $contains($safeStr($prop($, 'bundle_path')), '/Users/')
1442
+ and (
1443
+ $contains($safeStr($prop($, 'bundle_path')), '/Downloads/')
1444
+ or $contains($safeStr($prop($, 'bundle_path')), '/Desktop/')
1445
+ or $contains($safeStr($prop($, 'bundle_path')), '/tmp/')
1446
+ )
1447
+ )
1448
+ ]
1449
+ location: |
1450
+ {
1451
+ "bomRef": $."bom-ref",
1452
+ "purl": purl
1453
+ }
1454
+ message: "Running app '{{ name }}' originates from a risky user path: {{ $prop($, 'bundle_path') }}"
1455
+ mitigation: "Validate the app origin, move approved software into managed application paths, and investigate unexpected user-land execution."
1456
+ evidence: |
1457
+ {
1458
+ "bundlePath": $prop($, 'bundle_path'),
1459
+ "bundleExecutable": $prop($, 'bundle_executable'),
1460
+ "isFinishedLaunching": $prop($, 'is_finished_launching')
1461
+ }
1462
+
1463
+ - id: OBOM-MAC-007
1464
+ name: "macOS startup or application artifact failed notarization assessment"
1465
+ description: "Launchd, startup, and application artifacts with rejected notarization assessment deserve review before they are treated as trusted software."
1466
+ severity: high
1467
+ category: obom-runtime
1468
+ dry-run-support: full
1469
+ condition: |
1470
+ components[
1471
+ (
1472
+ (
1473
+ (
1474
+ $prop($, 'cdx:osquery:category') = 'launchd_services'
1475
+ or $prop($, 'cdx:osquery:category') = 'startup_items'
1476
+ )
1477
+ and (
1478
+ $not(
1479
+ $isDarwinSystemPath(
1480
+ $firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))
1481
+ )
1482
+ )
1483
+ or $not(
1484
+ $isDarwinSystemPath(
1485
+ $firstNonEmpty(
1486
+ $prop($, 'program'),
1487
+ $prop($, 'bundle_executable'),
1488
+ $prop($, 'bundle_path'),
1489
+ $prop($, 'path')
1490
+ )
1491
+ )
1492
+ )
1493
+ )
1494
+ )
1495
+ or (
1496
+ $prop($, 'cdx:osquery:category') = 'running_apps'
1497
+ and $not(
1498
+ $isDarwinSystemPath(
1499
+ $firstNonEmpty($prop($, 'bundle_path'), $prop($, 'path'))
1500
+ )
1501
+ )
1502
+ )
1503
+ )
1504
+ and $hasProp($, 'cdx:darwin:notarization:assessment')
1505
+ and $lowercase($safeStr($prop($, 'cdx:darwin:notarization:assessment'))) = 'rejected'
1506
+ ]
1507
+ location: |
1508
+ {
1509
+ "bomRef": $."bom-ref",
1510
+ "purl": purl
1511
+ }
1512
+ message: "macOS {{ $prop($, 'cdx:osquery:category') }} artifact '{{ name }}' uses registration path '{{ $firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'), name) }}' and target '{{ $firstNonEmpty($prop($, 'program'), $prop($, 'bundle_executable'), $prop($, 'bundle_path'), $prop($, 'path'), name) }}' with notarization assessment {{ $prop($, 'cdx:darwin:notarization:assessment') }}"
1513
+ mitigation: "Review the registration/config path and backing executable together, confirm the signer or team identifier against approved inventory, and remove or quarantine unexpected startup items or app bundles."
1514
+ evidence: |
1515
+ {
1516
+ "queryCategory": $prop($, 'cdx:osquery:category'),
1517
+ "registrationPath": $firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path')),
1518
+ "targetPath": $firstNonEmpty($prop($, 'program'), $prop($, 'bundle_executable'), $prop($, 'bundle_path'), $prop($, 'path')),
1519
+ "label": $prop($, 'label'),
1520
+ "path": $prop($, 'path'),
1521
+ "bundlePath": $prop($, 'bundle_path'),
1522
+ "bundleExecutable": $prop($, 'bundle_executable'),
1523
+ "program": $prop($, 'program'),
1524
+ "programArguments": $prop($, 'program_arguments'),
1525
+ "teamIdentifier": $prop($, 'cdx:darwin:codesign:teamIdentifier'),
1526
+ "notarizationAssessment": $prop($, 'cdx:darwin:notarization:assessment')
1527
+ }
1528
+
1529
+ - id: OBOM-MAC-008
1530
+ name: "macOS user-controlled startup or application artifact has unknown notarization assessment"
1531
+ description: "Launchd, startup, and application artifacts with unknown notarization assessment should be reviewed when they execute from user-controlled macOS paths."
1532
+ severity: medium
1533
+ category: obom-runtime
1534
+ dry-run-support: full
1535
+ condition: |
1536
+ components[
1537
+ (
1538
+ (
1539
+ (
1540
+ $prop($, 'cdx:osquery:category') = 'launchd_services'
1541
+ or $prop($, 'cdx:osquery:category') = 'startup_items'
1542
+ )
1543
+ and (
1544
+ $not(
1545
+ $isDarwinSystemPath(
1546
+ $firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))
1547
+ )
1548
+ )
1549
+ or $not(
1550
+ $isDarwinSystemPath(
1551
+ $firstNonEmpty(
1552
+ $prop($, 'program'),
1553
+ $prop($, 'bundle_executable'),
1554
+ $prop($, 'bundle_path'),
1555
+ $prop($, 'path')
1556
+ )
1557
+ )
1558
+ )
1559
+ )
1560
+ )
1561
+ or (
1562
+ $prop($, 'cdx:osquery:category') = 'running_apps'
1563
+ and $not(
1564
+ $isDarwinSystemPath(
1565
+ $firstNonEmpty($prop($, 'bundle_path'), $prop($, 'path'))
1566
+ )
1567
+ )
1568
+ )
1569
+ )
1570
+ and $hasProp($, 'cdx:darwin:notarization:assessment')
1571
+ and $lowercase($safeStr($prop($, 'cdx:darwin:notarization:assessment'))) = 'unknown'
1572
+ and (
1573
+ $contains(
1574
+ $lowercase($firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))),
1575
+ '/users/'
1576
+ )
1577
+ or $contains(
1578
+ $lowercase(
1579
+ $firstNonEmpty(
1580
+ $prop($, 'program'),
1581
+ $prop($, 'bundle_executable'),
1582
+ $prop($, 'bundle_path'),
1583
+ $prop($, 'path')
1584
+ )
1585
+ ),
1586
+ '/users/'
1587
+ )
1588
+ or $contains(
1589
+ $lowercase($firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))),
1590
+ '/downloads/'
1591
+ )
1592
+ or $contains(
1593
+ $lowercase(
1594
+ $firstNonEmpty(
1595
+ $prop($, 'program'),
1596
+ $prop($, 'bundle_executable'),
1597
+ $prop($, 'bundle_path'),
1598
+ $prop($, 'path')
1599
+ )
1600
+ ),
1601
+ '/downloads/'
1602
+ )
1603
+ or $contains(
1604
+ $lowercase($firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))),
1605
+ '/desktop/'
1606
+ )
1607
+ or $contains(
1608
+ $lowercase(
1609
+ $firstNonEmpty(
1610
+ $prop($, 'program'),
1611
+ $prop($, 'bundle_executable'),
1612
+ $prop($, 'bundle_path'),
1613
+ $prop($, 'path')
1614
+ )
1615
+ ),
1616
+ '/desktop/'
1617
+ )
1618
+ or $contains(
1619
+ $lowercase($firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))),
1620
+ '/tmp/'
1621
+ )
1622
+ or $contains(
1623
+ $lowercase(
1624
+ $firstNonEmpty(
1625
+ $prop($, 'program'),
1626
+ $prop($, 'bundle_executable'),
1627
+ $prop($, 'bundle_path'),
1628
+ $prop($, 'path')
1629
+ )
1630
+ ),
1631
+ '/tmp/'
1632
+ )
1633
+ or $contains(
1634
+ $lowercase($firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'))),
1635
+ '/private/var/'
1636
+ )
1637
+ or $contains(
1638
+ $lowercase(
1639
+ $firstNonEmpty(
1640
+ $prop($, 'program'),
1641
+ $prop($, 'bundle_executable'),
1642
+ $prop($, 'bundle_path'),
1643
+ $prop($, 'path')
1644
+ )
1645
+ ),
1646
+ '/private/var/'
1647
+ )
1648
+ )
1649
+ ]
1650
+ location: |
1651
+ {
1652
+ "bomRef": $."bom-ref",
1653
+ "purl": purl
1654
+ }
1655
+ message: "macOS {{ $prop($, 'cdx:osquery:category') }} artifact '{{ name }}' uses registration path '{{ $firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path'), name) }}' and target '{{ $firstNonEmpty($prop($, 'program'), $prop($, 'bundle_executable'), $prop($, 'bundle_path'), $prop($, 'path'), name) }}' with unknown notarization assessment on a user-controlled path"
1656
+ mitigation: "Review the registration/config path and backing executable together, re-check notarization and code-signing metadata, and move approved software out of user-controlled paths before suppressing the finding."
1657
+ evidence: |
1658
+ {
1659
+ "queryCategory": $prop($, 'cdx:osquery:category'),
1660
+ "registrationPath": $firstNonEmpty($prop($, 'path'), $prop($, 'bundle_path')),
1661
+ "targetPath": $firstNonEmpty($prop($, 'program'), $prop($, 'bundle_executable'), $prop($, 'bundle_path'), $prop($, 'path')),
1662
+ "label": $prop($, 'label'),
1663
+ "path": $prop($, 'path'),
1664
+ "bundlePath": $prop($, 'bundle_path'),
1665
+ "bundleExecutable": $prop($, 'bundle_executable'),
1666
+ "program": $prop($, 'program'),
1667
+ "programArguments": $prop($, 'program_arguments'),
1668
+ "teamIdentifier": $prop($, 'cdx:darwin:codesign:teamIdentifier'),
1669
+ "notarizationAssessment": $prop($, 'cdx:darwin:notarization:assessment')
1670
+ }
1671
+
1672
+ - id: OBOM-LNX-020
1673
+ name: "Privileged Linux listener exposed on a non-local interface from writable or unclassified path"
1674
+ description: "Root or service-account listeners bound to all interfaces from user-controlled or unclassified paths are high-signal persistence or runtime-drift indicators."
1675
+ severity: high
1676
+ category: obom-runtime
1677
+ dry-run-support: full
1678
+ condition: |
1679
+ components[
1680
+ $prop($, 'cdx:osquery:category') = 'privileged_listening_ports'
1681
+ and (
1682
+ $safeStr($prop($, 'address')) = '0.0.0.0'
1683
+ or $safeStr($prop($, 'address')) = '::'
1684
+ )
1685
+ and $safeStr($prop($, 'port')) != '22'
1686
+ and $safeStr($prop($, 'port')) != '53'
1687
+ and $safeStr(name) != 'systemd-resolved'
1688
+ and $safeStr(name) != 'avahi-daemon'
1689
+ and $safeStr(name) != 'cupsd'
1690
+ and (
1691
+ $safeStr($prop($, 'package_source_hint')) = 'user-writable-path'
1692
+ or $safeStr($prop($, 'package_source_hint')) = 'unclassified-path'
1693
+ or $contains($lowercase($nullSafeProp($, 'path')), '/tmp/')
1694
+ or $contains($lowercase($nullSafeProp($, 'path')), '/var/tmp/')
1695
+ or $contains($lowercase($nullSafeProp($, 'path')), '/dev/shm/')
1696
+ or $contains($lowercase($nullSafeProp($, 'path')), '/home/')
1697
+ or $contains($lowercase($nullSafeProp($, 'path')), '/run/user/')
1698
+ )
1699
+ ]
1700
+ location: |
1701
+ {
1702
+ "bomRef": $."bom-ref",
1703
+ "purl": purl
1704
+ }
1705
+ message: "Privileged listener '{{ name }}' is reachable on {{ $prop($, 'address') }}:{{ $prop($, 'port') }} from risky path '{{ $firstNonEmpty($prop($, 'path'), name) }}'"
1706
+ mitigation: "Treat the listener path as a high-priority review item, validate package ownership and recent changes, and remove or isolate privileged services sourced from writable or unclassified locations."
1707
+ evidence: |
1708
+ {
1709
+ "account": $prop($, 'account'),
1710
+ "pid": $prop($, 'pid'),
1711
+ "address": $prop($, 'address'),
1712
+ "port": $prop($, 'port'),
1713
+ "path": $prop($, 'path'),
1714
+ "serviceUnit": $prop($, 'service_unit'),
1715
+ "packageSourceHint": $prop($, 'package_source_hint'),
1716
+ "parentCmdline": $prop($, 'parent_cmdline')
1717
+ }
1718
+
1719
+ - id: OBOM-LNX-021
1720
+ name: "Linux APT source uses plaintext HTTP transport"
1721
+ description: "Plain HTTP APT mirrors weaken transport integrity and are often called out in baseline hardening reviews even when package signatures remain enabled."
1722
+ severity: medium
1723
+ category: obom-runtime
1724
+ dry-run-support: full
1725
+ condition: |
1726
+ components[
1727
+ (
1728
+ $prop($, 'cdx:osquery:category') = 'apt_sources'
1729
+ or $prop($, 'cdx:osquery:category') = 'apt_ppa_sources'
1730
+ )
1731
+ and $startsWith($lowercase($safeStr($prop($, 'base_uri'))), 'http://')
1732
+ ]
1733
+ location: |
1734
+ {
1735
+ "bomRef": $."bom-ref",
1736
+ "purl": purl,
1737
+ "file": $prop($, 'source')
1738
+ }
1739
+ message: "APT source '{{ name }}' still uses plaintext HTTP transport: {{ $prop($, 'base_uri') }}"
1740
+ mitigation: "Move the repository to HTTPS or an authenticated local mirror, then confirm the source file and mirror policy match your approved package-trust baseline."
1741
+ evidence: |
1742
+ {
1743
+ "sourceFile": $prop($, 'source'),
1744
+ "baseUri": $prop($, 'base_uri'),
1745
+ "release": $prop($, 'release'),
1746
+ "components": $prop($, 'components'),
1747
+ "maintainer": $prop($, 'maintainer')
1748
+ }
1749
+
1750
+ - id: OBOM-LNX-022
1751
+ name: "Linux authorized_keys entry uses deprecated ssh-rsa algorithm"
1752
+ description: "ssh-rsa authorized_keys entries rely on an older signature algorithm profile and should be reviewed during SSH hardening work."
1753
+ severity: medium
1754
+ category: obom-runtime
1755
+ dry-run-support: full
1756
+ condition: |
1757
+ components[
1758
+ $prop($, 'cdx:osquery:category') = 'authorized_keys_snapshot'
1759
+ and $lowercase($safeStr(version)) = 'ssh-rsa'
1760
+ ]
1761
+ location: |
1762
+ {
1763
+ "bomRef": $."bom-ref",
1764
+ "purl": purl,
1765
+ "file": $prop($, 'key_file')
1766
+ }
1767
+ message: "Authorized key for account '{{ name }}' in '{{ $prop($, 'key_file') }}' still uses deprecated ssh-rsa"
1768
+ mitigation: "Replace the key with ed25519 or a modern RSA/SHA-2 compatible key, then re-review key restrictions and account ownership before retaining access."
1769
+ evidence: |
1770
+ {
1771
+ "account": name,
1772
+ "algorithm": version,
1773
+ "keyFile": $prop($, 'key_file'),
1774
+ "comment": description,
1775
+ "uid": $prop($, 'uid')
1776
+ }