Commit 60ff9c9
Claude/calm security gaps z3hlla (#57)
* Close P0 trust gaps: verify_change TOCTOU, HTTP capability firewall, ledger HMAC, permissions, risk_rules, memory quarantine
Fixes and hardens the highest-severity gaps found in a code-level audit
comparing this repo's actual behavior against its "safety net" claims:
- verify_change now binds to the transaction's proposed_digest (checked
before AND after cargo check runs), closing a TOCTOU where a concurrent
write could get bound to someone else's verification receipt
- run_cargo_check now has a wall-clock timeout (config.verification.
timeout_secs, default 120s) instead of blocking indefinitely on a hung
build.rs/proc-macro/registry fetch
- Non-loopback `calm serve --http` now forces a capability-derived
"remote-safe" preset (every tool with read_only_hint=true, computed
live off the tool router) instead of "full,-edit", which only ever
excluded edit_lines/edit_symbol/format_files -- remember, verify_change,
retry_maintenance, scip_refresh, lsp_refresh, set_toolset, and
pattern_debt_register were all still reachable over an authenticated
remote connection despite the "read-only" framing
- The audit ledger is now HMAC-SHA256-signed (a new 0600 .calm/audit.key)
instead of a plain unkeyed SHA-256 chain -- SQLite file write access
alone can no longer forge a chain that still passes verify_chain
- `calm init` creates .calm/ atomically at 0700 (matching the daemon's
own posture) instead of an umask-derived create_dir_all; `calm doctor
--fix` retightens an already-loose .calm/ and its sensitive files
- `calm setup --npx` pins to this binary's own version by default instead
of an unpinned `npx -y @eilodon/calm-mcp` (--track latest opts out)
- New `.calm/config.json` risk_rules: a path-glob-to-minimum-risk floor
so a low-fan-in but security-sensitive file (auth/, CI workflows,
migrations) can't read as low risk purely because few callers exist yet
- `remember` quarantines injection-flagged notes; `recall` excludes them
from its ambient/broad paths (query search, list-all) by default,
mirroring edit_context's existing related_notes ambient-surfacing gate
- KNOWN_LIMITATIONS.md: an honest catalog of what's still open (sandboxed
multi-language verification, multi-file change-sets, a reference-impact
tool, change-kind-aware risk, structured evidence grounding, per-
connection daemon profiles, the CLI name collision, Git/CI integration)
and why each is deliberately deferred rather than half-built
All new/changed behavior covered by tests (cargo test --workspace,
including new integration tests spawning the real binary); cargo clippy
--workspace --all-targets -D warnings clean; fmt clean on every touched
file; doc-truth/gen-status/claims-registry checks and this repo's own
fitness-check all pass.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01GQRHnBxA3q9pCt77dHHRUB
* Close Tier 1+2 security/UX gaps: indexer DoS caps, signature-aware risk gate, HTTP hardening, reference_impact tool, structured edit citation
- Indexer now skips files over 8 MiB before reading them and bounds a
single tree-sitter parse to 5s, closing two concrete gaps behind
SECURITY.md's "malicious repo indexing DoS" stance.
- compute_touch_risk escalates risk to "high" when an edit's own proposed
content actually changes a touched function/method's signature text
(semantic comparison, not just line overlap -- a whole-body replace that
leaves the signature untouched no longer false-positives).
- calm serve --http now caps request body size and concurrent in-flight
requests as defense-in-depth (still not a substitute for a reverse
proxy's real rate limiting).
- New reference_impact tool merges call edges, import edges, and a
textual grep into one classified reference list for rename/removal
planning -- closes the exact gap behind two real
benchmarks/b7_task_correctness misses (a bare re-export invisible to
the call graph alone).
- edit_lines/edit_symbol gained an optional `cites` param: an exact
qualified-name match against edit_context's fresh caller list, closing
the "paste a caller name into an unrelated sentence" gaming path for
callers that opt in; the free-text `reason` path remains for backward
compatibility.
- KNOWN_LIMITATIONS.md, CHANGELOG.md, and all doc-truth-checked tool-count
references updated to match (35 -> 36 tools).
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01GQRHnBxA3q9pCt77dHHRUB
---------
Co-authored-by: Eilodon <noreply@anthropic.com>1 parent 86e1aad commit 60ff9c9
42 files changed
Lines changed: 3486 additions & 199 deletions
File tree
- .claude-plugin
- crates
- calm-cli
- src
- tests
- calm-core/src
- db
- indexer
- calm-server
- src
- __toolsnaps__
- tools
- docs
- plugins/calm/.claude-plugin
Some content is hidden
Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
8 | 8 | | |
9 | 9 | | |
10 | 10 | | |
11 | | - | |
| 11 | + | |
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
15 | | - | |
| 15 | + | |
16 | 16 | | |
17 | 17 | | |
18 | 18 | | |
| |||
262 | 262 | | |
263 | 263 | | |
264 | 264 | | |
265 | | - | |
| 265 | + | |
266 | 266 | | |
267 | 267 | | |
268 | 268 | | |
| |||
288 | 288 | | |
289 | 289 | | |
290 | 290 | | |
291 | | - | |
| 291 | + | |
292 | 292 | | |
293 | 293 | | |
294 | | - | |
| 294 | + | |
295 | 295 | | |
296 | 296 | | |
297 | 297 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
9 | 9 | | |
10 | 10 | | |
11 | 11 | | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
12 | 26 | | |
13 | 27 | | |
14 | 28 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
17 | 17 | | |
18 | 18 | | |
19 | 19 | | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
| 26 | + | |
20 | 27 | | |
21 | 28 | | |
22 | 29 | | |
| |||
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
237 | 237 | | |
238 | 238 | | |
239 | 239 | | |
| 240 | + | |
| 241 | + | |
| 242 | + | |
| 243 | + | |
| 244 | + | |
| 245 | + | |
| 246 | + | |
| 247 | + | |
240 | 248 | | |
241 | 249 | | |
242 | 250 | | |
| |||
0 commit comments