Engines
Every engine sits in a tier, and the tier decides what the engine is allowed to claim. Only a deterministic proof can make a result verified.
- 13 engines
- 9 policy guards
- 3 results, each with an admission decision
Three tiers
- Tier 1
Proof engines
Can return VERIFIED
Always with a
6 enginesproof_ref. All except Symbolic. - Tier 2
Policy guards
Block or hold
Deterministic rules on inputs, context and tool calls. Never VERIFIED.
9 guards - Tier 3
Advisory engines
Signals for review
Heuristic and model-based results are recorded as
5 enginesadvisory_checks, never as VERIFIED.
Proof engines
Symbolic solvers and formal methods. For the claims they cover, an answer either has a reproducible proof or it is not verified.
The Stats engine (stats_verifier.py) runs statistical code in a sandbox and returns UNVERIFIABLE: running code successfully is not treated as verification. SecureCodeExecutor runs code; it does not verify it.
The core counts its engines by module, as listed under each row: 13 in all, because Logic has two.
Policy guards
Deterministic rules applied at runtime. The same input against the same policy always gives the same decision. Guards return block or hold decisions, never VERIFIED.
- SystemGuard
Shell commands and file paths
- ConfigGuard
Secrets in configuration
- RAGGuard
Retrieved context
- MCPPoisonGuard
MCP tool definitions
- ExfiltrationGuard
Outbound data
- SelfInitiatedCoTGuard
Reasoning flow
- SovereigntyGuard
Data residency and routing
- StartupHookGuard
Startup hooks
- ProcessVerifier
Process milestones such as IRAC
Advisory engines
For questions where no formal proof exists. Graph, Image and Consensus can return VERIFIED only on a deterministic sub-path that carries a proof_ref. A model fallback never overrides a deterministic result.
Every check returns the same shape
Since v6.0.0 every engine and guard returns a DiagnosticResult with three layers: an agent_message that is safe to show an agent, structured developer_fields with the evidence, and a proof_ref, a hash that binds a VERIFIED result to its proof.
status VERIFIED | UNVERIFIABLE | BLOCKEDagent_message safe for agents, no internalsdeveloper_fields structured evidence for developersproof_ref present only when status is VERIFIEDVERIFIEDAdmission: ADMIT or DENY
The claim was settled with a proof, and proof_ref is present. It is admitted only if it holds; a claim proven false or unsafe is denied, with the evidence.
UNVERIFIABLEAdmission: DENY
The claim could not be proven, for example from insufficient evidence, ambiguous input or model-only support. No proof_ref. Denied by default; a person or your policy can review it.
BLOCKEDAdmission: DENY
Verification could not be attempted or completed, for example from a parse error, a missing declaration or a security policy violation. No proof_ref. Denied.
Who enforces DENY? QWED returns the result and the admission decision; it does not stop anything by itself. Your integration enforces DENY, or a QWED product does it for you, as QWED Security does by failing the pull request check.
The spec names the admission values ADMIT and DENY. The core library still calls DENY “BLOCKED” in one place; that is being aligned.
Other checks
Taint analysis follows untrusted input through generated code and flags it before it reaches a sensitive sink such as SQL or a shell. Domain packages such as qwed-finance add their own checks on top of these engines.