* chore: Exclude CLAUDE.md from Cargo.toml

* feat: add callgraph module and integrate into main analysis flow

* feat: enhance CLI with new severity filtering and analysis modes

* feat: update CHANGELOG with recent enhancements and fixes to severity filtering and output handling

* feat: implement state-model dataflow analysis for resource lifecycle and auth state

* feat: enhance diagnostic output formatting and add evidence structure

* feat: implement attack surface ranking for diagnostics with scoring and sorting

* feat: add comprehensive documentation for installation, usage, and rules reference

* feat: add multiple language support for command execution and evaluation endpoints

* feat: implement inline suppression for findings using `nyx:ignore` comments

* feat: add confidence levels to AST patterns and update output structure

* feat: implement low-noise prioritization system with category filtering, rollup grouping, and configurable budgets

* feat: bump version to 0.4.0 and update changelog with new features and improvements

* feat: add dead code allowances to various functions in mod.rs and real_world_tests.rs
This commit is contained in:
Eli Peter 2026-02-25 21:16:36 -05:00 committed by GitHub
parent 19b578c5c4
commit 1bbe4b1cfb
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
456 changed files with 25628 additions and 1228 deletions

View file

@ -0,0 +1,25 @@
{
"description": "File handle leaked in else branch of conditional",
"tags": [
"state",
"resource-leak",
"branch",
"file-io"
],
"modes": [
"full"
],
"expected": [
{
"rule_id": "state-resource-leak-possible",
"severity": null,
"must_match": false,
"line_range": [
1,
13
],
"evidence_contains": [],
"notes": "File handle closed in if branch but leaked in else branch"
}
]
}

View file

@ -0,0 +1,11 @@
import os
def conditional_open(path, flag):
f = open(path, 'r')
if flag:
data = f.read()
f.close()
return data
else:
return "skipped"
# f leaked in else branch

View file

@ -0,0 +1,48 @@
{
"description": "File handle lifecycle patterns: leak, proper close, double close, use after close",
"tags": [
"state",
"resource-leak",
"double-close",
"use-after-close",
"file-io"
],
"modes": [
"full"
],
"expected": [
{
"rule_id": "state-resource-leak",
"severity": null,
"must_match": false,
"line_range": [
1,
6
],
"evidence_contains": [],
"notes": "read_and_leak opens file but never closes it"
},
{
"rule_id": "state-double-close",
"severity": null,
"must_match": false,
"line_range": [
10,
17
],
"evidence_contains": [],
"notes": "double_close calls f.close() twice"
},
{
"rule_id": "state-use-after-close",
"severity": null,
"must_match": false,
"line_range": [
15,
23
],
"evidence_contains": [],
"notes": "use_after_close reads from file handle after closing it"
}
]
}

View file

@ -0,0 +1,21 @@
def read_and_leak(path):
f = open(path, 'r')
data = f.read()
return data
def read_and_close(path):
f = open(path, 'r')
data = f.read()
f.close()
return data
def double_close(path):
f = open(path, 'r')
f.close()
f.close()
def use_after_close(path):
f = open(path, 'r')
f.close()
data = f.read()
return data

View file

@ -0,0 +1,24 @@
{
"description": "Socket resource lifecycle - leaked vs properly closed with try/finally",
"tags": [
"state",
"resource-leak",
"socket"
],
"modes": [
"full"
],
"expected": [
{
"rule_id": "state-resource-leak",
"severity": null,
"must_match": false,
"line_range": [
1,
10
],
"evidence_contains": [],
"notes": "connect_and_leak creates socket but never closes it"
}
]
}

View file

@ -0,0 +1,18 @@
import socket
def connect_and_leak(host, port):
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((host, port))
s.send(b'hello')
data = s.recv(1024)
return data
def connect_and_close(host, port):
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((host, port))
try:
s.send(b'hello')
data = s.recv(1024)
return data
finally:
s.close()

View file

@ -0,0 +1,25 @@
{
"description": "Context manager vs manual open - else branch leaks file handle",
"tags": [
"state",
"resource-leak",
"context-manager",
"file-io"
],
"modes": [
"full"
],
"expected": [
{
"rule_id": "state-resource-leak",
"severity": null,
"must_match": false,
"line_range": [
12,
19
],
"evidence_contains": [],
"notes": "else branch opens file manually and never closes it"
}
]
}

View file

@ -0,0 +1,17 @@
def safe_with(path):
with open(path, 'r') as f:
return f.read()
def nested_with(src, dst):
with open(src, 'r') as reader:
with open(dst, 'w') as writer:
writer.write(reader.read())
def conditional_with(path, mode):
if mode == 'read':
with open(path, 'r') as f:
return f.read()
else:
f = open(path, 'w')
f.write('default')
# f not closed in else branch