@provos/ironcurtain 0.11.0 → 0.13.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.
- package/README.md +23 -19
- package/dist/cli-help.d.ts +12 -0
- package/dist/cli-help.js +21 -0
- package/dist/cli-help.js.map +1 -1
- package/dist/cli.js +14 -6
- package/dist/cli.js.map +1 -1
- package/dist/config/agent-model-guard.d.ts +14 -0
- package/dist/config/agent-model-guard.js +24 -0
- package/dist/config/agent-model-guard.js.map +1 -0
- package/dist/config/config-command.d.ts +33 -1
- package/dist/config/config-command.js +723 -11
- package/dist/config/config-command.js.map +1 -1
- package/dist/config/first-start.js +2 -8
- package/dist/config/first-start.js.map +1 -1
- package/dist/config/model-provider.d.ts +9 -0
- package/dist/config/model-provider.js +13 -0
- package/dist/config/model-provider.js.map +1 -1
- package/dist/config/openrouter-catalog.d.ts +46 -0
- package/dist/config/openrouter-catalog.js +111 -0
- package/dist/config/openrouter-catalog.js.map +1 -0
- package/dist/config/openrouter-models-fallback.d.ts +15 -0
- package/dist/config/openrouter-models-fallback.js +49 -0
- package/dist/config/openrouter-models-fallback.js.map +1 -0
- package/dist/config/paths.d.ts +48 -6
- package/dist/config/paths.js +63 -8
- package/dist/config/paths.js.map +1 -1
- package/dist/config/types.d.ts +8 -0
- package/dist/config/user-config.d.ts +179 -6
- package/dist/config/user-config.js +282 -5
- package/dist/config/user-config.js.map +1 -1
- package/dist/daemon/daemon-command.js +14 -5
- package/dist/daemon/daemon-command.js.map +1 -1
- package/dist/daemon/ironcurtain-daemon.d.ts +18 -0
- package/dist/daemon/ironcurtain-daemon.js +28 -1
- package/dist/daemon/ironcurtain-daemon.js.map +1 -1
- package/dist/daemon-client/daemon-client.d.ts +123 -0
- package/dist/daemon-client/daemon-client.js +324 -0
- package/dist/daemon-client/daemon-client.js.map +1 -0
- package/dist/docker/adapters/claude-code.js +109 -1
- package/dist/docker/adapters/claude-code.js.map +1 -1
- package/dist/docker/adapters/codex.d.ts +18 -0
- package/dist/docker/adapters/codex.js +376 -0
- package/dist/docker/adapters/codex.js.map +1 -0
- package/dist/docker/adapters/goose.js +38 -2
- package/dist/docker/adapters/goose.js.map +1 -1
- package/dist/docker/agent-adapter.d.ts +34 -6
- package/dist/docker/agent-adapter.js +2 -0
- package/dist/docker/agent-adapter.js.map +1 -1
- package/dist/docker/agent-registry.js +5 -0
- package/dist/docker/agent-registry.js.map +1 -1
- package/dist/docker/apple-container-manager.d.ts +49 -0
- package/dist/docker/apple-container-manager.js +486 -0
- package/dist/docker/apple-container-manager.js.map +1 -0
- package/dist/docker/ca.js +9 -2
- package/dist/docker/ca.js.map +1 -1
- package/dist/docker/code-mode-proxy.d.ts +11 -0
- package/dist/docker/code-mode-proxy.js +3 -1
- package/dist/docker/code-mode-proxy.js.map +1 -1
- package/dist/docker/container-lifecycle.d.ts +2 -2
- package/dist/docker/container-lifecycle.js +9 -0
- package/dist/docker/container-lifecycle.js.map +1 -1
- package/dist/docker/container-runtime.d.ts +29 -0
- package/dist/docker/container-runtime.js +76 -0
- package/dist/docker/container-runtime.js.map +1 -0
- package/dist/docker/docker-agent-session.d.ts +31 -0
- package/dist/docker/docker-agent-session.js +97 -7
- package/dist/docker/docker-agent-session.js.map +1 -1
- package/dist/docker/docker-infrastructure.d.ts +232 -15
- package/dist/docker/docker-infrastructure.js +762 -118
- package/dist/docker/docker-infrastructure.js.map +1 -1
- package/dist/docker/docker-manager.d.ts +25 -5
- package/dist/docker/docker-manager.js +388 -21
- package/dist/docker/docker-manager.js.map +1 -1
- package/dist/docker/docker-probe.d.ts +45 -0
- package/dist/docker/docker-probe.js +86 -0
- package/dist/docker/docker-probe.js.map +1 -0
- package/dist/docker/docker-progress-sink.d.ts +1 -1
- package/dist/docker/docker-resource-lifecycle.d.ts +71 -0
- package/dist/docker/docker-resource-lifecycle.js +454 -0
- package/dist/docker/docker-resource-lifecycle.js.map +1 -0
- package/dist/docker/gc-command.d.ts +2 -0
- package/dist/docker/gc-command.js +37 -0
- package/dist/docker/gc-command.js.map +1 -0
- package/dist/docker/mitm-proxy.d.ts +58 -5
- package/dist/docker/mitm-proxy.js +338 -26
- package/dist/docker/mitm-proxy.js.map +1 -1
- package/dist/docker/network-topology.d.ts +88 -0
- package/dist/docker/network-topology.js +167 -0
- package/dist/docker/network-topology.js.map +1 -0
- package/dist/docker/oauth-credentials.d.ts +13 -0
- package/dist/docker/oauth-credentials.js +125 -0
- package/dist/docker/oauth-credentials.js.map +1 -1
- package/dist/docker/openrouter.d.ts +107 -0
- package/dist/docker/openrouter.js +236 -0
- package/dist/docker/openrouter.js.map +1 -0
- package/dist/docker/orientation.js +1 -1
- package/dist/docker/orientation.js.map +1 -1
- package/dist/docker/package-types.d.ts +1 -1
- package/dist/docker/platform.d.ts +3 -1
- package/dist/docker/platform.js +3 -1
- package/dist/docker/platform.js.map +1 -1
- package/dist/docker/provider-config.d.ts +35 -1
- package/dist/docker/provider-config.js +93 -3
- package/dist/docker/provider-config.js.map +1 -1
- package/dist/docker/provision-lock.d.ts +46 -0
- package/dist/docker/provision-lock.js +152 -0
- package/dist/docker/provision-lock.js.map +1 -0
- package/dist/docker/pty-session.d.ts +22 -0
- package/dist/docker/pty-session.js +238 -84
- package/dist/docker/pty-session.js.map +1 -1
- package/dist/docker/pty-types.d.ts +15 -0
- package/dist/docker/pty-types.js +8 -0
- package/dist/docker/pty-types.js.map +1 -1
- package/dist/docker/registry-proxy.d.ts +46 -0
- package/dist/docker/registry-proxy.js +255 -1
- package/dist/docker/registry-proxy.js.map +1 -1
- package/dist/docker/resource-limits.d.ts +14 -5
- package/dist/docker/resource-limits.js +11 -8
- package/dist/docker/resource-limits.js.map +1 -1
- package/dist/docker/sse-extractor.js +55 -5
- package/dist/docker/sse-extractor.js.map +1 -1
- package/dist/docker/stream-delay.d.ts +86 -0
- package/dist/docker/stream-delay.js +218 -0
- package/dist/docker/stream-delay.js.map +1 -0
- package/dist/docker/token-stream-types.d.ts +15 -0
- package/dist/docker/trajectory-capture.d.ts +79 -0
- package/dist/docker/trajectory-capture.js +521 -0
- package/dist/docker/trajectory-capture.js.map +1 -0
- package/dist/docker/trajectory-reassembler.d.ts +286 -0
- package/dist/docker/trajectory-reassembler.js +1010 -0
- package/dist/docker/trajectory-reassembler.js.map +1 -0
- package/dist/docker/trajectory-tap.d.ts +100 -0
- package/dist/docker/trajectory-tap.js +410 -0
- package/dist/docker/trajectory-tap.js.map +1 -0
- package/dist/docker/trajectory-types.d.ts +187 -0
- package/dist/docker/trajectory-types.js +43 -0
- package/dist/docker/trajectory-types.js.map +1 -0
- package/dist/docker/types.d.ts +116 -12
- package/dist/doctor/checks.d.ts +39 -6
- package/dist/doctor/checks.js +129 -25
- package/dist/doctor/checks.js.map +1 -1
- package/dist/doctor/doctor-command.js +39 -9
- package/dist/doctor/doctor-command.js.map +1 -1
- package/dist/doctor/mcp-liveness.d.ts +1 -1
- package/dist/doctor/mcp-liveness.js +12 -4
- package/dist/doctor/mcp-liveness.js.map +1 -1
- package/dist/escalation/escalation-watcher.js +6 -0
- package/dist/escalation/escalation-watcher.js.map +1 -1
- package/dist/{mux → escalation}/trusted-input.d.ts +7 -4
- package/dist/{mux → escalation}/trusted-input.js +8 -5
- package/dist/escalation/trusted-input.js.map +1 -0
- package/dist/hash.js.map +1 -1
- package/dist/index.js +65 -16
- package/dist/index.js.map +1 -1
- package/dist/mux/mux-app.d.ts +9 -0
- package/dist/mux/mux-app.js +18 -16
- package/dist/mux/mux-app.js.map +1 -1
- package/dist/mux/mux-command.js +26 -8
- package/dist/mux/mux-command.js.map +1 -1
- package/dist/mux/mux-input-handler.d.ts +26 -2
- package/dist/mux/mux-input-handler.js +93 -11
- package/dist/mux/mux-input-handler.js.map +1 -1
- package/dist/mux/mux-renderer.d.ts +2 -1
- package/dist/mux/mux-renderer.js +67 -0
- package/dist/mux/mux-renderer.js.map +1 -1
- package/dist/mux/provider-profile-snapshot.d.ts +44 -0
- package/dist/mux/provider-profile-snapshot.js +56 -0
- package/dist/mux/provider-profile-snapshot.js.map +1 -0
- package/dist/mux/types.d.ts +3 -2
- package/dist/mux/types.js +6 -2
- package/dist/mux/types.js.map +1 -1
- package/dist/observe/observe-command.js +112 -125
- package/dist/observe/observe-command.js.map +1 -1
- package/dist/persona/broad-policy-validator.d.ts +95 -0
- package/dist/persona/broad-policy-validator.js +171 -0
- package/dist/persona/broad-policy-validator.js.map +1 -0
- package/dist/persona/compile-persona-policy.d.ts +54 -2
- package/dist/persona/compile-persona-policy.js +29 -4
- package/dist/persona/compile-persona-policy.js.map +1 -1
- package/dist/persona/event-bus-progress-reporter.d.ts +57 -0
- package/dist/persona/event-bus-progress-reporter.js +66 -0
- package/dist/persona/event-bus-progress-reporter.js.map +1 -0
- package/dist/persona/persona-command.js +46 -76
- package/dist/persona/persona-command.js.map +1 -1
- package/dist/persona/persona-compile-orchestrator.d.ts +101 -0
- package/dist/persona/persona-compile-orchestrator.js +504 -0
- package/dist/persona/persona-compile-orchestrator.js.map +1 -0
- package/dist/persona/persona-service.d.ts +137 -0
- package/dist/persona/persona-service.js +263 -0
- package/dist/persona/persona-service.js.map +1 -0
- package/dist/persona/policy-mutation-audit.d.ts +109 -0
- package/dist/persona/policy-mutation-audit.js +179 -0
- package/dist/persona/policy-mutation-audit.js.map +1 -0
- package/dist/persona/rule-delta.d.ts +30 -0
- package/dist/persona/rule-delta.js +82 -0
- package/dist/persona/rule-delta.js.map +1 -0
- package/dist/persona/types.d.ts +12 -0
- package/dist/pipeline/annotate.js +10 -2
- package/dist/pipeline/annotate.js.map +1 -1
- package/dist/pipeline/compile.js +14 -2
- package/dist/pipeline/compile.js.map +1 -1
- package/dist/pipeline/constitution-compiler.js.map +1 -1
- package/dist/pipeline/generate-with-repair.js.map +1 -1
- package/dist/pipeline/pipeline-runner.d.ts +63 -4
- package/dist/pipeline/pipeline-runner.js +159 -50
- package/dist/pipeline/pipeline-runner.js.map +1 -1
- package/dist/pipeline/pipeline-shared.d.ts +32 -3
- package/dist/pipeline/pipeline-shared.js +76 -8
- package/dist/pipeline/pipeline-shared.js.map +1 -1
- package/dist/pipeline/refresh-lists.js +3 -5
- package/dist/pipeline/refresh-lists.js.map +1 -1
- package/dist/pipeline/scenario-schema-validator.js.map +1 -1
- package/dist/{mux → pty}/pty-bridge.d.ts +41 -3
- package/dist/{mux → pty}/pty-bridge.js +71 -18
- package/dist/pty/pty-bridge.js.map +1 -0
- package/dist/pty/resolve-ironcurtain-bin.d.ts +17 -0
- package/dist/pty/resolve-ironcurtain-bin.js +22 -0
- package/dist/pty/resolve-ironcurtain-bin.js.map +1 -0
- package/dist/sandbox/index.d.ts +19 -4
- package/dist/sandbox/index.js +31 -18
- package/dist/sandbox/index.js.map +1 -1
- package/dist/servers/fetch-server.js +2 -0
- package/dist/servers/fetch-server.js.map +1 -1
- package/dist/session/index.d.ts +1 -1
- package/dist/session/index.js +20 -2
- package/dist/session/index.js.map +1 -1
- package/dist/session/preflight.d.ts +20 -35
- package/dist/session/preflight.js +92 -109
- package/dist/session/preflight.js.map +1 -1
- package/dist/session/resource-budget-tracker.js +8 -0
- package/dist/session/resource-budget-tracker.js.map +1 -1
- package/dist/session/session-manager.d.ts +7 -0
- package/dist/session/session-manager.js.map +1 -1
- package/dist/session/types.d.ts +23 -0
- package/dist/signal/bot-command.js +6 -1
- package/dist/signal/bot-command.js.map +1 -1
- package/dist/signal/setup-signal.js +1 -1
- package/dist/signal/setup-signal.js.map +1 -1
- package/dist/signal/signal-bot-daemon.d.ts +1 -0
- package/dist/signal/signal-bot-daemon.js +9 -2
- package/dist/signal/signal-bot-daemon.js.map +1 -1
- package/dist/signal/signal-container.d.ts +3 -3
- package/dist/signal/signal-container.js +2 -2
- package/dist/signal/signal-container.js.map +1 -1
- package/dist/trusted-process/call-circuit-breaker.d.ts +6 -0
- package/dist/trusted-process/call-circuit-breaker.js +22 -3
- package/dist/trusted-process/call-circuit-breaker.js.map +1 -1
- package/dist/trusted-process/container-command.d.ts +35 -0
- package/dist/trusted-process/container-command.js +49 -0
- package/dist/trusted-process/container-command.js.map +1 -0
- package/dist/trusted-process/mcp-error-utils.js +4 -1
- package/dist/trusted-process/mcp-error-utils.js.map +1 -1
- package/dist/trusted-process/mcp-proxy-server.js +37 -3
- package/dist/trusted-process/mcp-proxy-server.js.map +1 -1
- package/dist/trusted-process/policy-engine.js +13 -2
- package/dist/trusted-process/policy-engine.js.map +1 -1
- package/dist/trusted-process/tcp-server-transport.d.ts +19 -1
- package/dist/trusted-process/tcp-server-transport.js +56 -10
- package/dist/trusted-process/tcp-server-transport.js.map +1 -1
- package/dist/trusted-process/tool-call-coordinator.d.ts +22 -8
- package/dist/trusted-process/tool-call-coordinator.js +149 -65
- package/dist/trusted-process/tool-call-coordinator.js.map +1 -1
- package/dist/trusted-process/tool-call-pipeline.d.ts +8 -0
- package/dist/trusted-process/tool-call-pipeline.js +68 -34
- package/dist/trusted-process/tool-call-pipeline.js.map +1 -1
- package/dist/util/atomic-write.d.ts +31 -0
- package/dist/util/atomic-write.js +43 -0
- package/dist/util/atomic-write.js.map +1 -0
- package/dist/utils/preflight-checks.js +1 -3
- package/dist/utils/preflight-checks.js.map +1 -1
- package/dist/utils/stdio-guard.d.ts +1 -0
- package/dist/utils/stdio-guard.js +27 -0
- package/dist/utils/stdio-guard.js.map +1 -0
- package/dist/web-ui/__tests__/config-dispatch.test.d.ts +13 -0
- package/dist/web-ui/__tests__/config-dispatch.test.js +383 -0
- package/dist/web-ui/__tests__/config-dispatch.test.js.map +1 -0
- package/dist/web-ui/__tests__/json-rpc-dispatch.test.js +6 -0
- package/dist/web-ui/__tests__/json-rpc-dispatch.test.js.map +1 -1
- package/dist/web-ui/conn-registry.d.ts +14 -0
- package/dist/web-ui/conn-registry.js +25 -0
- package/dist/web-ui/conn-registry.js.map +1 -0
- package/dist/web-ui/dispatch/config-dispatch.d.ts +15 -0
- package/dist/web-ui/dispatch/config-dispatch.js +277 -0
- package/dist/web-ui/dispatch/config-dispatch.js.map +1 -0
- package/dist/web-ui/dispatch/escalation-dispatch.js +11 -2
- package/dist/web-ui/dispatch/escalation-dispatch.js.map +1 -1
- package/dist/web-ui/dispatch/persona-dispatch.d.ts +46 -2
- package/dist/web-ui/dispatch/persona-dispatch.js +209 -56
- package/dist/web-ui/dispatch/persona-dispatch.js.map +1 -1
- package/dist/web-ui/dispatch/pty-dispatch.d.ts +15 -0
- package/dist/web-ui/dispatch/pty-dispatch.js +66 -0
- package/dist/web-ui/dispatch/pty-dispatch.js.map +1 -0
- package/dist/web-ui/dispatch/session-dispatch.js +89 -6
- package/dist/web-ui/dispatch/session-dispatch.js.map +1 -1
- package/dist/web-ui/dispatch/types.d.ts +35 -0
- package/dist/web-ui/dispatch/types.js +42 -1
- package/dist/web-ui/dispatch/types.js.map +1 -1
- package/dist/web-ui/dispatch/workflow-dispatch.js +116 -5
- package/dist/web-ui/dispatch/workflow-dispatch.js.map +1 -1
- package/dist/web-ui/json-rpc-dispatch.js +4 -1
- package/dist/web-ui/json-rpc-dispatch.js.map +1 -1
- package/dist/web-ui/pty-session-manager.d.ts +234 -0
- package/dist/web-ui/pty-session-manager.js +599 -0
- package/dist/web-ui/pty-session-manager.js.map +1 -0
- package/dist/web-ui/web-event-bus.d.ts +34 -1
- package/dist/web-ui/web-event-bus.js.map +1 -1
- package/dist/web-ui/web-session-transport.js.map +1 -1
- package/dist/web-ui/web-ui-server.d.ts +22 -0
- package/dist/web-ui/web-ui-server.js +41 -0
- package/dist/web-ui/web-ui-server.js.map +1 -1
- package/dist/web-ui/web-ui-types.d.ts +212 -5
- package/dist/web-ui/web-ui-types.js.map +1 -1
- package/dist/web-ui-static/assets/index-CCVI4nEK.css +1 -0
- package/dist/web-ui-static/assets/index-Dm012gvY.js +114 -0
- package/dist/web-ui-static/index.html +2 -2
- package/dist/workflow/cli-shared.d.ts +62 -0
- package/dist/workflow/cli-shared.js +117 -0
- package/dist/workflow/cli-shared.js.map +1 -0
- package/dist/workflow/cli-support.js +0 -2
- package/dist/workflow/cli-support.js.map +1 -1
- package/dist/workflow/container-snapshots.d.ts +29 -0
- package/dist/workflow/container-snapshots.js +137 -0
- package/dist/workflow/container-snapshots.js.map +1 -0
- package/dist/workflow/daemon-gate-commands.d.ts +21 -0
- package/dist/workflow/daemon-gate-commands.js +595 -0
- package/dist/workflow/daemon-gate-commands.js.map +1 -0
- package/dist/workflow/discovery.d.ts +29 -0
- package/dist/workflow/discovery.js +67 -7
- package/dist/workflow/discovery.js.map +1 -1
- package/dist/workflow/lane-template.d.ts +89 -0
- package/dist/workflow/lane-template.js +141 -0
- package/dist/workflow/lane-template.js.map +1 -0
- package/dist/workflow/lint.d.ts +7 -1
- package/dist/workflow/lint.js +186 -3
- package/dist/workflow/lint.js.map +1 -1
- package/dist/workflow/machine-builder.d.ts +90 -2
- package/dist/workflow/machine-builder.js +222 -29
- package/dist/workflow/machine-builder.js.map +1 -1
- package/dist/workflow/message-log.d.ts +15 -1
- package/dist/workflow/message-log.js.map +1 -1
- package/dist/workflow/orchestrator.d.ts +505 -1
- package/dist/workflow/orchestrator.js +1725 -69
- package/dist/workflow/orchestrator.js.map +1 -1
- package/dist/workflow/prompt-builder.js +2 -1
- package/dist/workflow/prompt-builder.js.map +1 -1
- package/dist/workflow/run-state-command.js +1 -1
- package/dist/workflow/run-state-command.js.map +1 -1
- package/dist/workflow/shutdown-signals.d.ts +7 -0
- package/dist/workflow/shutdown-signals.js +40 -0
- package/dist/workflow/shutdown-signals.js.map +1 -0
- package/dist/workflow/status-parser.js +19 -4
- package/dist/workflow/status-parser.js.map +1 -1
- package/dist/workflow/types.d.ts +123 -23
- package/dist/workflow/types.js +2 -0
- package/dist/workflow/types.js.map +1 -1
- package/dist/workflow/validate.d.ts +23 -1
- package/dist/workflow/validate.js +311 -22
- package/dist/workflow/validate.js.map +1 -1
- package/dist/workflow/workflow-command.d.ts +0 -17
- package/dist/workflow/workflow-command.js +118 -94
- package/dist/workflow/workflow-command.js.map +1 -1
- package/dist/workflow/workflow-discovery.d.ts +2 -0
- package/dist/workflow/workflow-discovery.js +22 -1
- package/dist/workflow/workflow-discovery.js.map +1 -1
- package/dist/workflow/workflow-manager.d.ts +34 -0
- package/dist/workflow/workflow-manager.js +52 -1
- package/dist/workflow/workflow-manager.js.map +1 -1
- package/dist/workflow/workflows/design-and-code/README.md +50 -0
- package/dist/workflow/workflows/deterministic-eval-smoke/scripts/format_report.js +29 -0
- package/dist/workflow/workflows/deterministic-eval-smoke/scripts/package.json +5 -0
- package/dist/workflow/workflows/deterministic-eval-smoke/scripts/requirements.txt +1 -0
- package/dist/workflow/workflows/deterministic-eval-smoke/scripts/run_eval.py +41 -0
- package/dist/workflow/workflows/deterministic-eval-smoke/workflow.yaml +57 -0
- package/dist/workflow/workflows/deterministic-verdict-smoke/scripts/classify.py +18 -0
- package/dist/workflow/workflows/deterministic-verdict-smoke/workflow.yaml +51 -0
- package/dist/workflow/workflows/evolve/README.md +66 -0
- package/dist/workflow/workflows/evolve/scripts/LICENSE +201 -0
- package/dist/workflow/workflows/evolve/scripts/README.md +314 -0
- package/dist/workflow/workflows/evolve/scripts/evolve-brief +16 -0
- package/dist/workflow/workflows/evolve/scripts/evolve-cognition +16 -0
- package/dist/workflow/workflows/evolve/scripts/evolve-db +16 -0
- package/dist/workflow/workflows/evolve/scripts/evolve-eval +16 -0
- package/dist/workflow/workflows/evolve/scripts/evolve-files +16 -0
- package/dist/workflow/workflows/evolve/scripts/evolve-summary +16 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/__init__.py +14 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/__init__.py +17 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/base.py +21 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/factory.py +90 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/greedy.py +17 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/island.py +316 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/random.py +18 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/algorithms/ucb1.py +55 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/best_snapshot.py +62 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/cli.py +752 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/cognition.py +127 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/database.py +218 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/diff.py +57 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/embedding.py +84 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/file_lock.py +45 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/run_state.py +343 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/sampling_config.py +173 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/structures.py +93 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_core/vector_index.py +191 -0
- package/dist/workflow/workflows/evolve/scripts/evolve_result.py +1503 -0
- package/dist/workflow/workflows/evolve/scripts/requirements.txt +2 -0
- package/dist/workflow/workflows/evolve/workflow.yaml +646 -0
- package/dist/workflow/workflows/test-email-summary/workflow.yaml +1 -0
- package/dist/workflow/workflows/vuln-discovery/README.md +54 -0
- package/dist/workflow/workflows/vuln-discovery/skills/harness-design-fuzzing/SKILL.md +6 -1
- package/dist/workflow/workflows/vuln-discovery/skills/memory-safety-c-cpp/SKILL.md +1 -0
- package/dist/workflow/workflows/vuln-discovery/skills/vulnerability-triage/SKILL.md +4 -0
- package/dist/workflow/workflows/vuln-discovery/workflow.yaml +13 -8
- package/docker/Dockerfile.base +22 -0
- package/docker/Dockerfile.base.arm64 +18 -0
- package/docker/Dockerfile.claude-code +3 -1
- package/docker/Dockerfile.codex +17 -0
- package/docker/Dockerfile.goose +3 -1
- package/docker/entrypoint-claude-code.sh +28 -45
- package/docker/entrypoint-codex.sh +42 -0
- package/docker/entrypoint-goose.sh +5 -24
- package/docker/entrypoint-uid-remap.sh +93 -0
- package/package.json +39 -30
- package/src/workflow/workflows/design-and-code/README.md +50 -0
- package/src/workflow/workflows/deterministic-eval-smoke/scripts/format_report.js +29 -0
- package/src/workflow/workflows/deterministic-eval-smoke/scripts/package.json +5 -0
- package/src/workflow/workflows/deterministic-eval-smoke/scripts/requirements.txt +1 -0
- package/src/workflow/workflows/deterministic-eval-smoke/scripts/run_eval.py +41 -0
- package/src/workflow/workflows/deterministic-eval-smoke/workflow.yaml +57 -0
- package/src/workflow/workflows/deterministic-verdict-smoke/scripts/classify.py +18 -0
- package/src/workflow/workflows/deterministic-verdict-smoke/workflow.yaml +51 -0
- package/src/workflow/workflows/evolve/README.md +66 -0
- package/src/workflow/workflows/evolve/scripts/LICENSE +201 -0
- package/src/workflow/workflows/evolve/scripts/README.md +314 -0
- package/src/workflow/workflows/evolve/scripts/evolve-brief +16 -0
- package/src/workflow/workflows/evolve/scripts/evolve-cognition +16 -0
- package/src/workflow/workflows/evolve/scripts/evolve-db +16 -0
- package/src/workflow/workflows/evolve/scripts/evolve-eval +16 -0
- package/src/workflow/workflows/evolve/scripts/evolve-files +16 -0
- package/src/workflow/workflows/evolve/scripts/evolve-summary +16 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/__init__.py +14 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/__init__.py +17 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/base.py +21 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/factory.py +90 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/greedy.py +17 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/island.py +316 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/random.py +18 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/algorithms/ucb1.py +55 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/best_snapshot.py +62 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/cli.py +752 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/cognition.py +127 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/database.py +218 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/diff.py +57 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/embedding.py +84 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/file_lock.py +45 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/run_state.py +343 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/sampling_config.py +173 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/structures.py +93 -0
- package/src/workflow/workflows/evolve/scripts/evolve_core/vector_index.py +191 -0
- package/src/workflow/workflows/evolve/scripts/evolve_result.py +1503 -0
- package/src/workflow/workflows/evolve/scripts/requirements.txt +2 -0
- package/src/workflow/workflows/evolve/workflow.yaml +646 -0
- package/src/workflow/workflows/test-email-summary/workflow.yaml +1 -0
- package/src/workflow/workflows/vuln-discovery/README.md +54 -0
- package/src/workflow/workflows/vuln-discovery/skills/harness-design-fuzzing/SKILL.md +6 -1
- package/src/workflow/workflows/vuln-discovery/skills/memory-safety-c-cpp/SKILL.md +1 -0
- package/src/workflow/workflows/vuln-discovery/skills/vulnerability-triage/SKILL.md +4 -0
- package/src/workflow/workflows/vuln-discovery/workflow.yaml +13 -8
- package/dist/mux/pty-bridge.js.map +0 -1
- package/dist/mux/trusted-input.js.map +0 -1
- package/dist/web-ui-static/assets/index-BFO5z1js.js +0 -76
- package/dist/web-ui-static/assets/index-CCUwrkIL.css +0 -1
- package/packages/web-ui/README.md +0 -113
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
# Vulnerability Discovery
|
|
2
|
+
|
|
3
|
+
An orchestrator-driven workflow that points a Docker-isolated `claude-code` agent at a body of code, **builds tiered instrumented harnesses, and tries to execute its way to a confirmed vulnerability** — analysis → harnessing → discovery → triage → report, with human gates whenever the machine gets stuck or finishes.
|
|
4
|
+
|
|
5
|
+
Run it from the web UI (**Start Workflow → `vuln-discovery`**) or the CLI:
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
ironcurtain workflow start vuln-discovery \
|
|
9
|
+
"find a memory-corruption bug reachable from a crafted H.264 stream" \
|
|
10
|
+
--workspace ~/src/ffmpeg
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
Point `--workspace` at a checkout of the code under investigation. The task description carries the **scope, vulnerability class, and threat model**; a one-liner like `"find a vulnerability in libavcodec/h264_slice.c"` is enough to start, since the agent prompts supply the methodology. Add detail to steer the hunt.
|
|
14
|
+
|
|
15
|
+
> **Requires Docker.** This workflow only runs in Docker Agent Mode (`--network=none`); there is no builtin-mode fallback. Run `ironcurtain doctor` first if you're unsure your environment is ready. For a fresh-checkout walkthrough (build, daemon, web UI, non-Anthropic models, troubleshooting) see [`docs/vuln-discovery-onboarding/README.md`](https://github.com/provos/ironcurtain/blob/master/docs/vuln-discovery-onboarding/README.md).
|
|
16
|
+
|
|
17
|
+
## What it does
|
|
18
|
+
|
|
19
|
+
The orchestrator sits at the center and decides what to do next each round, reading and updating the investigation journal. Around it, the agents move a hypothesis from structural understanding to an executed, triaged finding. All artifacts land under `.workflow/` in the workspace.
|
|
20
|
+
|
|
21
|
+
| Phase | State(s) | Role | Output |
|
|
22
|
+
| ----- | ------------------------------------------ | ---------------------------------------------------------------------------------------------------------------- | ----------------------------------------------- |
|
|
23
|
+
| 1 | `analyze` | Code analyst — maps call chains, entry points, build system, trust boundaries | `.workflow/analysis/analysis.md` |
|
|
24
|
+
| — | `orchestrator` | Strategist — picks the next state, enforces budget, owns the journal | `.workflow/journal/journal.md` |
|
|
25
|
+
| 2 | `harness_design` → `harness_design_review` | Architect + LLM reviewer — spec an instrumented, tiered harness | `.workflow/harness_design/` |
|
|
26
|
+
| 3 | `harness_build` → `harness_validate` | Engineer + verifier — implement the harness, confirm it runs and produces coverage | `.workflow/harness_build/`, `harness_validate/` |
|
|
27
|
+
| 4 | `discover` (+ `differential_validate`) | Researcher — hypothesis-driven search using the harness; diagnose isolated-vs-live divergence | `.workflow/discoveries/findings.h*.md` |
|
|
28
|
+
| 5 | `triage` | Independent reproducer — re-prove each finding and assess severity | `.workflow/triage/triage.h*.md` |
|
|
29
|
+
| 6 | `conclude` → `review` | Report writer + LLM reviewer — assemble the final report, catch scope drift and evidence/headline contradictions | `.workflow/report/report.md` |
|
|
30
|
+
|
|
31
|
+
## Human gates
|
|
32
|
+
|
|
33
|
+
Four gates pause the run for your decision. Each presents the relevant artifacts (journal, analysis, designs, reports) and accepts **APPROVE** (continue), **FORCE_REVISION** (loop back — your feedback is routed verbatim into the next agent's prompt, so brief it like an orchestrator), or **ABORT**.
|
|
34
|
+
|
|
35
|
+
- **`human_escalation`** — the orchestrator detected a stall (same state 3+ times, contradictory results, or no clear next direction). Give it another round, redirect it, or stop.
|
|
36
|
+
- **`harness_design_escalation`** — the design-review loop rejected the design 3× in a row. Accept the design as-is, redirect, or stop.
|
|
37
|
+
- **`harness_validate_escalation`** — the validate loop rejected the build 4× in a row. Accept the harness despite validation failures, redirect, or stop.
|
|
38
|
+
- **`report_review`** — the investigation reached `complete` and the final report is ready. Approve it, send it back (your assessment overrides the agent's — e.g. dispute a "mitigated" verdict and it re-investigates at a higher tier), or discard.
|
|
39
|
+
|
|
40
|
+
## The orchestration loop
|
|
41
|
+
|
|
42
|
+
Unlike a fixed pipeline, the **orchestrator** re-routes after every round based on the journal: forward when a harness validates and findings hold, back to re-design or re-discover when they don't. The loop is bounded by `maxRounds` (**12**) and `maxSessionSeconds` (**10800** = 3 hours). When either limit or a stall is hit, control surfaces to a human gate rather than spinning — it never loops forever.
|
|
43
|
+
|
|
44
|
+
## At a glance
|
|
45
|
+
|
|
46
|
+
- **Mode:** Docker (`claude-code` agent, `--network=none`, shared container)
|
|
47
|
+
- **Model:** `anthropic:claude-opus-4-8`
|
|
48
|
+
- **Persona:** `global` for every agent state
|
|
49
|
+
- **Caps:** 12 rounds · 3-hour session budget
|
|
50
|
+
- **Skills:** `memory-safety-c-cpp`, `harness-design-fuzzing`, `vulnerability-triage` (co-packaged under `skills/`)
|
|
51
|
+
- **Artifacts:** `analysis`, `journal`, `harness_*`, `discoveries`, `triage`, `report` — all under `.workflow/`
|
|
52
|
+
- **Terminal states:** `done` (report approved) · `aborted` (stopped at a gate)
|
|
53
|
+
|
|
54
|
+
> Tip: the more precisely the task states the **threat model** (who the attacker is, how input reaches the code), the less the analyst has to guess. "Memory corruption reachable from an untrusted network packet" steers the whole run; "find bugs" does not. To run bigger targets past the default caps, copy the whole `vuln-discovery/` directory (it carries the skills it needs) into `~/.ironcurtain/workflows/` and raise the limits there.
|
|
@@ -61,13 +61,15 @@ Use Tier 3 when the bug depends on initialization sequences, global state, runti
|
|
|
61
61
|
|
|
62
62
|
The harness must FUZZ, not unit-test. For each swept variable (hypothesis inputs for trigger-driven, dispatch axes for coverage-driven), the design must specify:
|
|
63
63
|
|
|
64
|
-
- **Sweep range.** The full range of values to iterate over. Cover the entire representable range of the type, not just "a few specific values." For wide ranges, specify dense sampling near type boundaries (min, max, zero, `2^N - 1` for each relevant N, sign-flip points) plus sparse sampling elsewhere. For coverage-driven dispatch axes, the range is the full set of dispatch values plus their realistic combinations.
|
|
64
|
+
- **Sweep range.** The full range of values to iterate over. Cover the entire representable range of the type, not just "a few specific values." For wide ranges, specify dense sampling near type boundaries (min, max, zero, `2^N - 1` for each relevant N, sign-flip points) plus sparse sampling elsewhere. When the variable feeds an allocation size through a product or other multi-term arithmetic, also sample values whose wrapped result is *small but positive*: these keep the consumer's loop/index bound large while the undersized allocation succeeds, whereas the value that wraps exactly to zero is usually intercepted by a separate zero-size guard. For coverage-driven dispatch axes, the range is the full set of dispatch values plus their realistic combinations.
|
|
65
65
|
- **Search strategy.** Exhaustive enumeration if the space is < 100M combinations; boundary-dense + random sampling otherwise; coverage-guided fuzzer for large or structured input spaces.
|
|
66
66
|
- **Observables.** At each input value, what does the harness record? Stored value in the target buffer, result of the bounds check at `<file>:<line>`, return value of the target function, sanitizer error, canary state, dispatch arm hit. Be specific by site.
|
|
67
67
|
- **Positive-finding condition.** What pattern in the observables confirms the design's claim? For trigger-driven: be specific — not "a crash happens" but "the bounds check at `<file>:<line>` evaluates true when the input value exceeds the buffer's allocated size." For coverage-driven: "any sanitizer error within the named code region" is acceptable, but the region must be concrete.
|
|
68
68
|
|
|
69
69
|
The design specifies input variables and ranges. The implementer drives the sweep. Do NOT prescribe individual "Test A / Test B / Test C" scenarios with fixed values — that's unit testing and will miss the actual boundary.
|
|
70
70
|
|
|
71
|
+
**Per-input cost bound.** A coverage-guided fuzzer needs many iterations per second to work. The design must keep per-input cost bounded: cap input size (libFuzzer `-max_len`, AFL++ `-G`), and keep the fuzz entry point free of full re-initialization, process spawns, or multi-connection sweeps — move one-time setup behind a `call_once` / singleton. If an oracle genuinely needs a many-connection or many-iteration measurement (e.g. RSS amplification), that is a *separate* harness, not per-input work folded into the sweep.
|
|
72
|
+
|
|
71
73
|
### Multi-hypothesis bundling
|
|
72
74
|
|
|
73
75
|
A trigger-driven design may scope a single hypothesis or a related set when they share input space and code region. Bundle when consolidating doesn't dilute the sweep (e.g., three integer-overflow hypotheses on the same allocator → one harness). Keep separate when input distributions conflict (one wants huge dimensions, another wants small) or observation points differ enough that one harness can't see both.
|
|
@@ -145,6 +147,8 @@ The harness MUST test against UNMODIFIED source code. Stripping a guard, weakeni
|
|
|
145
147
|
|
|
146
148
|
A Tier-1 harness with hardening stripped tells you nothing about production outcomes. Triage anchors on what the harness demonstrated under production-equivalent conditions.
|
|
147
149
|
|
|
150
|
+
Default the value-producing integer checks (overflow, shift, truncation) to **recover / warn-only mode**: aborting at the arithmetic site stops execution before any downstream undersized-allocation or out-of-bounds sink, masking the real impact and inviting a false "mitigated" verdict. Recover mode lets execution continue with the wrapped value (production behavior), so one run surfaces both the root-cause diagnostic and the sink.
|
|
151
|
+
|
|
148
152
|
## Delegate library realism
|
|
149
153
|
|
|
150
154
|
Mitigation discipline applies at the link layer too. A harness that links against a project-internal stub of an upstream library produces evidence about the stub, not about production. Every stub the design introduces must be classified.
|
|
@@ -174,6 +178,7 @@ List every external dependency (sanitizer toolchain, fuzzer binary, coverage too
|
|
|
174
178
|
- **Hand-picked positive scenarios masquerading as a sweep.** Five "boundary cases" are chosen by hand. The actual boundary in the target's arithmetic is not one of the five.
|
|
175
179
|
- **Hardening stripped for "easier debugging."** ASLR off, canaries off, custom permissive allocator. The harness fires; production does not. Tells you nothing.
|
|
176
180
|
- **Validator stubbed at link time.** A project-internal stub of a parser, validator, or decoder library is linked into the harness, omitting the upstream component's own validation. The harness fires; production rejects the trigger before the violation site is reached. Tells you nothing about reachability.
|
|
181
|
+
- **Per-input heavyweight setup.** The harness does a full handshake, fixture rebuild, or N-connection sweep inside the fuzz entry point, so it runs at single-digit exec/s — an integration test in a loop, not a fuzzer. The feedback loop never gets enough iterations to reach boundary values. Move one-time setup to a singleton; split a measurement oracle that needs many connections into its own non-fuzzed harness.
|
|
177
182
|
|
|
178
183
|
## Design-document scope
|
|
179
184
|
|
|
@@ -163,4 +163,5 @@ If any of the three cannot be answered from the artifacts alone, the finding is
|
|
|
163
163
|
- **Round-tripped attacker input mistaken for leaked target state.** If the bytes the bug "leaks" are bytes the attacker just sent, that is not a confidentiality finding. Memory-read findings need to demonstrate adjacency — what _target_ state sits next to the affected region.
|
|
164
164
|
- **Padding or zeroed memory mistaken for sensitive content.** A heap OOB read that returns NUL bytes, schema-sanitized placeholders, or default-config values has not demonstrated impact.
|
|
165
165
|
- **Hardening-stripped harness vs production binary.** A harness compiled without `-D_FORTIFY_SOURCE`, without stack canaries, without ASLR, or with custom allocators tells you nothing about the production binary's behavior. The triage question is "what does the production build do under this input," not "what does my Tier-1 reproduction show."
|
|
166
|
+
- **An abort at the arithmetic site mistaken for unreachability of the downstream sink.** In an overflow-into-undersized-allocation chain, a check that aborts at the overflow itself — an integer sanitizer in halt mode, or a precondition/zero-size guard that only fires when the value wraps exactly to zero — stops execution before the write, making the bug look pre-empted. Production builds wrap silently and reach the sink. Run the overflow checks in warn-only / recover mode (do not force-abort on them) so a single run surfaces both the root-cause diagnostic and the downstream sanitizer trip; or confirm on an allocation-sanitized build driven with a trigger whose wrapped value is small-positive. A "mitigated/pre-empted" verdict for an overflow-into-sink hypothesis is valid only when established on a build that lets execution continue past the overflow, not on the abort-at-overflow configuration.
|
|
166
167
|
- **Variant tunnel-vision.** Reporting only the variant the harness reproduced when the underlying pattern (e.g., the same arithmetic in a sibling dispatch handler) reaches more of the surface. Every variant is its own attack surface; document each.
|
|
@@ -43,6 +43,8 @@ For each finding, the rubric below has eleven items. Skipping any one of them is
|
|
|
43
43
|
|
|
44
44
|
6. **Production hardening.** What mitigations present in production (sanitizers, schema validators, CSP, ASLR, stack canaries, auth middleware, sandbox, rate limits, RELRO, FORTIFY_SOURCE) change the attacker's success rate? Did the experiment use the production profile or bypass it? A harness with hardening stripped tells you nothing about production outcomes — score what production does, not what the harness did.
|
|
45
45
|
|
|
46
|
+
When a mitigation table asserts a runtime cap, flag, or mode is at a particular default value in production, cite the line that *registers* that default (GObject property spec, struct initializer, constant read at startup) — not a call site that happens to leave it unset. A harness that overrides the default via the library's public API (`set_max_X(0)`, `set_strict(false)`) looks identical at the bug site to a real default of 0; the registration cite is what distinguishes them.
|
|
47
|
+
|
|
46
48
|
7. **External exploitability trace.** Does the input originate from an external / untrusted source, and through what delivery channel? Name it concretely — network protocol, file upload, queue consumer, environment-variable propagation, IPC. Complete answer: a named delivery channel from an untrusted boundary to the bug site. Incomplete: "an attacker could supply input" without naming how.
|
|
47
49
|
|
|
48
50
|
8. **Duplicate / CVE check.** Search the project's issue tracker, CVE databases, and changelog for the code location. Note overlap with existing fixes even when partial — a fix for one variant does not necessarily cover sibling variants.
|
|
@@ -162,6 +164,8 @@ Patterns the rubric catches that get missed in practice. These are surface-neutr
|
|
|
162
164
|
|
|
163
165
|
- **Hardening-stripped harness scored as production.** The harness ran without ASLR, without canaries, without FORTIFY_SOURCE, with a permissive custom allocator, or with the validating middleware bypassed. The production binary intercepts the effect; the harness did not see that interception. The Achievable / Environmental score is what production does, not what the harness did.
|
|
164
166
|
|
|
167
|
+
- **Harness API override mistaken for production default.** The harness called the library's public configuration API to lift a safety valve (`set_max_X(0)`, disable strict mode, suppress validation) so a latent bug becomes reachable — a legitimate research move. The mitigations table then asserts that the *production* default is the lifted value, conflating "the harness set it to 0" with "the default is 0". Distinct from compiler-hardening stripping: this is the library's own runtime configuration, and the registration site (property spec, initializer) is the ground truth, not the call-site override.
|
|
168
|
+
|
|
165
169
|
- **Theoretical ceiling promoted to demonstrated severity by rewording.** "This pattern *could* yield RCE" gets quoted, then rewritten without the hedge, then cited as "demonstrated RCE" two paragraphs later. The rubric's reproduction and effect-realism items refute this; the hedging-elimination rule names it.
|
|
166
170
|
|
|
167
171
|
- **Variant tunnel-vision.** The harness reproduced one variant of the underlying pattern; the finding reports only that variant. When the same arithmetic / lifetime / dispatch shape reaches sibling variants on the same surface, those are findings in their own right. Document each, even when the experiment exercised only one.
|
|
@@ -6,7 +6,7 @@ settings:
|
|
|
6
6
|
mode: docker
|
|
7
7
|
dockerAgent: claude-code
|
|
8
8
|
sharedContainer: true
|
|
9
|
-
model: anthropic:claude-opus-4-
|
|
9
|
+
model: anthropic:claude-opus-4-8
|
|
10
10
|
maxRounds: 12
|
|
11
11
|
maxSessionSeconds: 10800
|
|
12
12
|
unversionedArtifacts:
|
|
@@ -162,11 +162,12 @@ states:
|
|
|
162
162
|
|
|
163
163
|
**If discover returned `approved` (confirmed):** route to `triage` if the evidence is solid, or back to `discover` for more evidence if it is thin.
|
|
164
164
|
|
|
165
|
-
**If discover returned `blocked` (mitigated or exhausted):** the "mitigated" claim is authoritative only when
|
|
165
|
+
**If discover returned `blocked` (mitigated or exhausted):** the "mitigated" claim is authoritative only when ALL of:
|
|
166
166
|
- The tier matched the hypothesis scope — cross-component hypotheses require Tier 2+.
|
|
167
167
|
- Evidence shows execution, not reasoning: coverage of the mitigation code AND a completed input sweep over the hypothesis's value range (fuzzing for value-dependent claims, bounded enumeration for discrete claims).
|
|
168
|
+
- The mitigation was exercised, not just present. If non-impact is attributed to an invariant the harness had to disable to reach the site (a concurrency/serialization contract, an upstream guard, a runtime/allocator check, or a first-abort that shadows a later sink), the claim holds only if discover ran the trigger under a configuration where that invariant is present and showed the effect absorbed there. An invariant-only mitigation backed by source reading is the masked-finding pattern — non-terminal.
|
|
168
169
|
|
|
169
|
-
If the evidence is text-only ("the code looks safe"), re-route to `discover` to exercise
|
|
170
|
+
If the evidence is text-only ("the code looks safe") or the mitigation rests on an un-exercised invariant, re-route to `discover` to exercise it under an invariant-present config, or to `harness_design` at a higher tier if the harness cannot. If no invariant-present config that still reaches the site can be built, treat the evidence as insufficient and keep the hypothesis open — do NOT record it as a terminal `harness-tested-and-rejected`; route to `harness_design` for an alternative reachability approach, or defer the hypothesis with an explicit reason. ("Insufficient" here describes the evidence; it is not a routing verdict to emit.)
|
|
170
171
|
|
|
171
172
|
**If discover returned `rejected` (couldn't run):**
|
|
172
173
|
- Coverage shows the target function IS reached but the condition doesn't fire → `differential_validate` (values need adjustment for the live context: protocol encoding, byte order, framing).
|
|
@@ -330,7 +331,7 @@ states:
|
|
|
330
331
|
|
|
331
332
|
Do NOT include:
|
|
332
333
|
- Full C/Python/etc. source code for the harness
|
|
333
|
-
- Build scripts or compile commands with full flag lists (reference them abstractly: "compile with ASAN+UBSAN")
|
|
334
|
+
- Build scripts or compile commands with full flag lists (reference them abstractly: "compile with ASAN+UBSAN, integer checks in recover/warn-only mode")
|
|
334
335
|
- Test execution results or tables of "expected outcomes" — you haven't run anything yet
|
|
335
336
|
|
|
336
337
|
DO include:
|
|
@@ -485,6 +486,8 @@ states:
|
|
|
485
486
|
|
|
486
487
|
The harness should be invocable as a CLI tool or script. The discovery agent needs to: start a session, perform multiple steps, observe coverage, and reset cleanly.
|
|
487
488
|
|
|
489
|
+
**Bounded harness execution (required).** Every command that runs the built harness — reset check, smoke/baseline run, instrumentation probe, any burst — MUST be wrapped in a hard-kill wall-clock guard: `timeout -s KILL <seconds> <command>`. Plain `timeout` sends a catchable SIGTERM that a wedged harness can defer or ignore; only `-s KILL` (or `-k`) guarantees termination. This is tool-agnostic — it holds whether the harness is a fuzzer, a bounded enumerator, an analyzer, or a one-shot driver.
|
|
490
|
+
|
|
488
491
|
**Instrumentation verification (required before approved).** Confirm fuzzer-feedback is present on the target, not only the harness. Method depends on the mechanism:
|
|
489
492
|
- Compile-time (libFuzzer / sanitizer-coverage): `nm` / `readelf` the target archive and expect symbols like `__sanitizer_cov_trace_pc_guard` in the target's object files.
|
|
490
493
|
- Compile-wrapper (AFL++): instrumented objects contain `__afl_area_ptr`; `afl-showmap` on a baseline reports non-trivial map density (≫100 edges).
|
|
@@ -523,15 +526,17 @@ states:
|
|
|
523
526
|
2. **Linkage audit (gating).** Run `ldd` (Linux), `otool -L` (macOS), or the platform equivalent against the test binary. Confirm no shared library resolves to a project-internal stub directory (typical names: `*-stub/`, `*_mock/`, `mock-*/`, `fake-*/`). If linkage resolves to a project-internal stub of any component performing trust-boundary validation in production (parser, validator, decoder, signature checker, schema validator), return `rejected_design` regardless of coverage and crash signals. Cite the specific link path and stub component in the rejection. The linkage check is gating: it runs before the coverage and crash gates and short-circuits on failure.
|
|
524
527
|
3. **Baseline run.** Run the harness with a simple benign input. Verify it exits without errors.
|
|
525
528
|
4. **Target function reached.** Run the harness coverage command. Verify the **target function** (not just the target file) appears with non-zero hits. If the file has coverage but the function does not, the call chain is broken — fail.
|
|
526
|
-
5. **Fuzzer-feedback reach (load-bearing).** Run a short representative fuzz burst (30–60s) from the seed corpus. Capture the fuzzer's own reported coverage metric:
|
|
529
|
+
5. **Fuzzer-feedback reach (load-bearing).** Run a short representative fuzz burst (30–60s) from the seed corpus. Run it in the FOREGROUND under a hard kill guard — `timeout -s KILL <burst+30s>` wrapping the binary — and pass the fuzzer's own watchdogs (libFuzzer: `-max_total_time=<burst> -timeout=20 -rss_limit_mb=4096`; AFL++: the `-V` / `-t` / `-m` equivalents). Plain `timeout` sends a catchable SIGTERM that a slow fuzzer defers between iterations — it will not stop a wedged burst. Do NOT background the burst and poll with a `pgrep`/`sleep` loop: `pgrep -af <name>` matches the poll command's own arguments, so the loop never exits. Capture the fuzzer's own reported coverage metric:
|
|
527
530
|
- libFuzzer (also the tools that wrap its output: jazzer.js, atheris, cargo-fuzz, Jazzer): stderr prints `#N ... cov: C ft: F`. Record `C`.
|
|
528
531
|
- AFL++: `afl-fuzz` reports `map density` / `edges found`; `afl-showmap` on a sample prints non-zero map entries. Record the edge count.
|
|
529
532
|
- For any other tool, the design must name the exact metric field (see harness_design coverage-instrumentation rules). If the design does not name it, that is a design defect — route `rejected_design` with a directive "design.md must specify the fuzzer-feedback metric field name for the chosen tool."
|
|
530
|
-
Fail approval unless
|
|
533
|
+
Fail approval unless ALL of:
|
|
531
534
|
(a) Target-code fuzzer-feedback count ≥ **1000** (default; configurable via directive). A count in the tens is the signature of wrapper-only instrumentation. For tools reporting in different units, interpret the threshold as "several orders of magnitude larger than a thin wrapper's footprint" and state the equivalent number used.
|
|
532
535
|
(b) Audit-coverage line coverage of the target source file ≥ **20%** (default; configurable via directive) after the burst.
|
|
536
|
+
(c) Burst throughput is not pathological: record `exec/s` and the slowest-unit time. `exec/s` in the single digits, or any single unit exceeding ~10s, means the harness is too slow to fuzz — a per-input heavyweight-setup defect that both wedges the burst's own time limit and would wedge `discover`.
|
|
533
537
|
If (a) fails: target code was not instrumented for fuzzer feedback — diagnose build vs. design.
|
|
534
538
|
If (b) fails but (a) passes: seed corpus is too narrow — route to `harness_design` for seed-corpus revision.
|
|
539
|
+
If (c) fails: route `rejected_design` with directive "cap input size (`-max_len`) and move per-input heavyweight setup (full re-init, process spawn, multi-connection sweep) out of the fuzz entry point."
|
|
535
540
|
6. **Stateful session sanity.** If the harness supports multi-step sessions, run a short sequence; verify state persists.
|
|
536
541
|
7. **Branch-level audit coverage exists.** Confirm the audit tool reports branch data, not just line counts.
|
|
537
542
|
|
|
@@ -596,7 +601,7 @@ states:
|
|
|
596
601
|
The orchestrator's directive tells you what to test. Use the harness to:
|
|
597
602
|
|
|
598
603
|
1. **Design an input sequence** that exercises the hypothesized code path. Use the analysis's function catalog for guidance on types, boundaries, and assumptions.
|
|
599
|
-
2. **Send it through the harness** and observe results. Read coverage to see which lines and branches were hit. Check for sanitizer output, crashes, and invariant violations.
|
|
604
|
+
2. **Send it through the harness** and observe results. Read coverage to see which lines and branches were hit. Check for sanitizer output, crashes, and invariant violations. If you run ANY work in the background (fuzz campaign, build, etc.), wait on the launched PID (`cmd & PID=$!; wait "$PID"`); never poll with a `pgrep -f <name>`/`sleep` loop (`pgrep -f` matches the waiter's own command line and your prompt-bearing agent process, so the loop never exits) and never poll a hardcoded log/output path you did not capture from that same launch.
|
|
600
605
|
3. **Refine or pivot.** If coverage shows you missed the target path, adjust inputs to hit the right branch. If you reached it with no violation, try variations before moving to a new hypothesis.
|
|
601
606
|
4. **Repeat systematically.** Work through the hypotheses in the orchestrator's directive.
|
|
602
607
|
|
|
@@ -608,7 +613,7 @@ states:
|
|
|
608
613
|
|
|
609
614
|
- **approved**: An exploitable condition fired — sanitizer error, controlled crash, invariant violation, or direct evidence the hypothesized bug triggered. Document the reproduction input, coverage proof, and severity.
|
|
610
615
|
- **rejected**: The harness is insufficient — can't reach the target, missing protocol feature, broken infrastructure.
|
|
611
|
-
- **blocked**: Hypothesis did not fire despite a completed search. You may only return `blocked` if (a) coverage shows the target code was executed, AND (b) you swept the input range relevant to the hypothesis — fuzzing for value-dependent claims (sizes, offsets, indices, counters), bounded enumeration for discrete claims (protocol states, flag combinations, auth paths). "I read the code and it looks mitigated" is not `blocked` — it's `rejected` with a request to redesign the harness. If neither fuzzing nor enumeration applies to this hypothesis, name the reason explicitly in your findings doc.
|
|
616
|
+
- **blocked**: Hypothesis did not fire despite a completed search. You may only return `blocked` if (a) coverage shows the target code was executed, AND (b) you swept the input range relevant to the hypothesis — fuzzing for value-dependent claims (sizes, offsets, indices, counters), bounded enumeration for discrete claims (protocol states, flag combinations, auth paths). "I read the code and it looks mitigated" is not `blocked` — it's `rejected` with a request to redesign the harness. If neither fuzzing nor enumeration applies to this hypothesis, name the reason explicitly in your findings doc. **Invariant-only mitigations are not `blocked`.** If you attribute non-impact to an invariant your harness had to disable to reach the site — a lock/serialization or single-threaded dispatch contract, an upstream guard, a runtime/allocator check, or an earlier sanitizer abort that prevents reaching a downstream sink — you may return `blocked` only if you ALSO ran the trigger under a configuration where that invariant is present and showed the effect absorbed there. Disabling the invariant to reach the site and then citing it as the mitigation is circular; if you cannot build an invariant-present config that still reaches the site, return `blocked` only for the part you exercised and name the un-exercised invariant explicitly.
|
|
612
617
|
|
|
613
618
|
Write per-hypothesis findings to `.workflow/discoveries/findings.<id>.md` where `<id>` is the orchestrator's hypothesis ID — e.g. `findings.h1.md`, `findings.h2.md`. Do not collapse hypotheses into one file. Append after each experiment (hypothesis, input, harness command, result) before starting the next one — do not batch writes to the end, so a crash or rate-limit preserves the round's work. If a hypothesis's findings file already exists from a prior run, read it first and skip experiments whose results are already recorded; do not re-read other hypotheses' files unless the directive scopes you to them.
|
|
614
619
|
inputs:
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"pty-bridge.js","sourceRoot":"","sources":["../../src/mux/pty-bridge.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"trusted-input.js","sourceRoot":"","sources":["../../src/mux/trusted-input.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,mBAAmB,EAAE,MAAM,qCAAqC,CAAC;AAC1E,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAcpC;;;;;;GAMG;AACH,MAAM,UAAU,uBAAuB,CAAC,aAAqB,EAAE,WAAmB;IAChF,MAAM,WAAW,GAAG,OAAO,CAAC,aAAa,EAAE,mBAAmB,CAAC,CAAC;IAChE,MAAM,OAAO,GAAuB;QAClC,WAAW;QACX,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;QACnC,MAAM,EAAE,mBAAmB;KAC5B,CAAC;IACF,mBAAmB,CAAC,WAAW,EAAE,OAAO,CAAC,CAAC;AAC5C,CAAC"}
|