Continuous Correctness Audit
Install Proof on one consequential component.
Find the bugs your tests missed. In about four weeks, you get approved requirements, confirmed findings with reproducers, agent-ready fix context, and a gate in your CI that keeps checking every change.
Explore a live graph → seeded product demo; read the labels first
01 · The shape
One component. Fixed fee. About four weeks.
A Continuous Correctness Audit is a standing engagement against a written bar. We formalize the requirements for one component you choose with us, your engineers approve them, and we prove and test the code against every approved clause.
Scope
one component
Install
roughly four weeks
Price
fixed after scoping
Decision owner
about two hours in week one
Engineering team
about two hours a week while we install
The fee is quoted at scoping and fixed before work starts, and it covers re-verification of the fixes you land during the install. Everything the install produces is yours, whether or not you continue.
The claim is bounded on purpose: within a declared scope, for declared behaviors, with evidence commensurate with the consequence of failure. A person validates every finding before you see it, so we take a small number of engagements at a time.
The audit is how Proof gets installed. Proof is what stays. The graph, the records and the gate keep running whether or not the engagement continues. The install is the component-level way to begin. The other two ways, one real change or ten unresolved items from one component, start from a demo request. What Proof is, in full, is on the product page.
02 · Approval
Your engineers approve the promises.
Nothing is judged against a requirement your engineers have not approved. We draft, the owners of the component approve, and only then can a clause fail a build. The drafting is ours, which is why approval costs the decision owner about two hours in week one.
- Week 0
Scope one component, countersign the NDA
We agree the shape and the fee before work starts. We countersign your NDA before reading a line.
- Week 1
Requirements the owners approve
We index the code first, then its history and the places intent lives: the tracker, the support queue, the docs nobody updated. Your engineers approve every requirement before any code is judged.
- Weeks 2–3
Worst cases, obligations, evidence, first findings
Approved requirements become formal properties. We check the specification itself for realizability, consistency and vacuity, so a bad clause cannot condemn good code. Where code and approved requirements disagree, we write it up.
- From week 4
The gate goes live
The evidence corpus lands in your repository and the gate wires into your CI: a broken requirement blocks the merge. We walk your team through every finding and every proof. That is the end of the install, not of the audit.
A person validates every finding before you see it. Agents do more of the crunching every month; a person stays on the line between machine and judgment.
From your side
What we need from you.
Three things. Proof reads your code; it does not write it.
Two or three engineers who own the component
About two hours a week while we install. They know what the code is meant to do; we write it down with them.
A repository we can read
Public, or private under NDA with read-only access. Private stays private.
One person who can approve
You set an assurance level on every requirement. Proof ships with all of them open to an agent, and every approval records the agent and the level. Reserve the levels you want a person on — one setting in proof.yaml — and those wait for someone who owns the code.
03 · The findings
Every confirmed issue arrives ready to fix.
A confirmed issue is a record in your repository that carries the work of reproducing itself. An engineer or a coding agent can start on it without a triage call first.
Violated intent
The approved requirement the code fails, named by its identifier. The finding argues against a clause your engineers signed off.
Expected, observed
What the requirement promises, and what the code does at the input that breaks it.
A reproducer
A test and a command you can paste. No reproducer, no finding. A finding you cannot re-run is an opinion with formatting.
Severity, and its basis
Our assessment, weighted by reachability and impact, with the basis recorded on the entry. A starting point for your triage.
Blast radius
The files, the tests, the parent requirement and the obligations a fix will have to re-earn, answered before the edit.
An agent-ready prompt
The same record framed as a task, with the reproducer as the finish line. What the agent receives →
Validation
We ran the reproducer before delivery and recorded the result of that run. A person validated the finding before it reached you.
After the fix
The issue becomes a verified defect record, and the reproducer stays in your CI as a permanent regression test. How change and defect records work →
A real one
KI-3, on the public jsonparser project.
Filed by this audit against buger/jsonparser, fixed on master, and readable in full on the public register.
Known issue
KI-3 status: fixed
Violated intent
SYS-REQ-009: Set must update the addressed JSON value without corrupting unrelated structure.
Observed
Malformed JSON output on array-index paths under object parents.
Reproducer
set_spec_test.go, run with go test -run TestSetArrayIndexUnderObjectMalformedJSON_KI3. While the bug was live the test asserted the broken output; it was flipped at the fix, so a regression trips it either way.
Severity
High, basis: reproducer. Our assessment, weighted by reachability and impact.
Fix
Landed in parser.go. The reproducer stays in CI as the regression test.
Record
DEFECT-260726-MFPA, which keeps the root cause, the hardening and the retest.
Follow the whole chain, file by file → The public register →
04 · What stays
The graph and gate stay in your repository.
The install does not end in a report. It ends in a graph of what the component must do, bound to the code that implements it, the evidence that supports it, the issues that remain open and the changes that follow. All of it lands in your repository, under your licence, in formats your CI already runs.
The graph
Requirements, hazards, obligations, code, documentation and evidence hang off the component that owns them. Select a component, a requirement, a known issue or a change, and the graph answers what it rests on and what rests on it.
Blast radius
Before anyone touches the code, the graph answers what else is being touched: which files, which tests, which parent requirement, which obligations have to be re-earned.
Change records
Every change records why the behavior changed, which component owns it, which requirements it introduced or affected, and which evidence made the result acceptable. A commit says what text moved; a change record says what the system now promises.
Defect records
Open problems stay known issues. A verified fix turns one into a defect record that keeps the fix and its evidence together.
Self-invalidation
When code, documentation or a dependency moves, the affected evidence goes stale. Proof does not declare the requirement false. It withdraws yesterday's confidence until the affected obligations are reviewed or rerun.
Agent access
Your coding agents read the same components, requirements, dependencies, obligations and evidence your engineers read — served over MCP to any MCP client. The agent starts from approved intent instead of rediscovering the system from raw code. What the agent receives →
Fig. 01 · What the install builds: one component, its requirements, its open issues and its change history, with the evidence bound to each.
- If this changes
-
- 5 files
- 13 tests
- 1 parent requirement
- related obligations
The blast radius is answered before the edit, not discovered after the release.
The corpus
Plain files, in your git.
Requirements, source annotations, tests, findings, coverage evidence and formal logs. The graph is not a hosted secret: the dashboard is a window over the corpus, and the corpus leaves with you.
your-repo/ ├── specs/ │ └── <component>.req.yaml ← approved by your engineers ├── src/… ← // SW-REQ-XXX ├── tests/… ← // Verifies: SW-REQ-XXX ├── changes/ │ ├── CHANGE-XXXX.yaml ← what the behavior now promises │ └── DEFECT-XXXX.yaml ← the fix and its evidence ├── evidence/ │ ├── findings/F-XXX_test.go ← runnable, and it pins the break │ ├── coverage/<component>/ ← condition-level coverage │ └── formal/<component>.log └── .github/workflows/proof.yml ← the gate
On the public project the paths are specs/{stakeholder,system}/requirements/, proof/known-issues/, proof/problem-reports/ and proof/evidence/ — open them.
Reproducers, regression pins, condition-level coverage (MC/DC), formal checks on the requirements, plain YAML and executable tests. Prefer no hosted portal? The same views ship as generated static reports.
Seeded product demo proof-demo, our showcase branch on the probelabs/jsonparser fork, captured 3 August 2026. Its open findings are demonstration entries, deliberately left broken; the fixed records are the real ones. Listed as a limitation.
05 · The standing audit
The standing audit keeps the evidence current.
The four weeks are the expensive part: intent recovered, requirements approved, proofs built, the gate wired. What they buy is a corpus that makes every audit after them fast.
From week five the audit runs monthly at a flat fee, on the cadence you choose, per release, weekly, even daily: new and changed code held to the approved requirements, new behavior formalized into new clauses, every break a finding with a runnable reproducer, the register current for anyone who asks what is open.
The gate reruns mechanically on every merge regardless. The cadence you buy is how often an auditor reads what changed, extends the bar, and re-judges severities. By month twelve, the graph normally carries more approved intent, historical defects, and retained evidence than it did in month one. Each quarter, one more component comes under the bar, install-grade, sized into the retainer at scoping.
After week four, the register does the work. Known issues become scheduled fixes the gate grades: your engineers, your coding agents working from the attached prompts, or our fix sprints when you want the queue off your plate. When a customer reports a bug, you check the register before you open a debugger.
One passing reproducer can prove the known instance is gone. Closing the whole defect class takes broader evidence: the sibling sweep, the hazard evidence, and the blast-radius verification behind it. When a defect slips through, the miss is recorded in the customer's register and the bar is widened. Misses from public Proof work are published. Private engagement evidence remains private unless the customer explicitly authorizes disclosure.
The install is priced as the expensive part precisely because everything after it is flat and compounding.
Read the method → What the corpus is worth in year two →
The record
What you keep when people change.
People move teams. Agents get swapped for better agents. The requirement your engineer approved stays where it is, and the gate keeps checking it.
Fig. 02 · A promise enters the record. It is still checked after the author leaves or the agent is swapped.
06 · Independence
Fix work stays separate from audit.
Fix work is never bundled into the audit. The audit fee never depends on finding volume or remediation volume. Every fix, including ours, must satisfy the same approved requirements and the same customer-owned evidence gate.
The audit reads your code; it does not write it. Only fix work writes, and only through pull requests you accept.
Every register entry ships an agent-ready prompt with the reproducer as the finish line, so your engineers or your coding agents can burn the queue down at no further cost. When you want the queue off your plate, fix sprints are scoped and priced separately, and delivered as pull requests your engineers review and merge.
The gate grades our fixes exactly as it grades anyone's. A fix that does not satisfy the approved requirement does not merge, whoever wrote it.
07 · Five commitments
Five commitments, written into the engagement.
Not aspirations. Each one is a term of the engagement, and each one is checkable by you.
- Reproducer guarantee. No reproducer, no finding. Runnable or it does not ship. Every finding arrives with a reproducer we ran before delivery and the recorded result of that run, and a person validated it before it reached you. A reproducer pins the finding one of two ways: it fails until the fix lands, or it asserts the broken behavior while that behavior is live and flips when the fix lands. The record says which.
- Severity escalation. A finding we assess at our highest severity reaches your named contact within one business day of validation. It does not wait for the weekly report.
- Regression guarantee. Every fixed defect becomes a regression test in your CI. If the defect returns, your build fails before anyone has to remember it existed.
- Bounded claims, in writing. The scope, the behaviors and the depth of evidence are written into the contract. We sign what we checked and nothing beyond it.
- Zero lock-in. The gate runs without us. The corpus is plain YAML and executable tests in your git. If you cancel, everything that runs stays yours; what ends is our ongoing involvement.
08 · Exclusions
What we will not claim.
The list below is part of the offer. An audit that will not say what it cannot see is not worth buying.
- This is not a certified penetration test, and it does not satisfy a compliance requirement for one. Security promises inside the scoped component are audited like any other; black-box red-teaming, infrastructure testing, and social engineering stay with the security firms.
- Dependencies are held to their declared contracts. Auditing a dependency's internals is its own scope, quoted separately when you need it.
- This does not replace static analysis. Pattern scanners catch known bug shapes cheaply; keep them running. We audit against requirements the owners approved, which no scanner has read.
- We will not claim total correctness. No audit can. Our signature covers the declared scope and declared behaviors at the stated depth of evidence, and it stops there.
- Performance is out of scope. Throughput, latency and capacity belong with your performance engineers.
- Severity labels are ours: our assessment, weighted by reachability and impact; a starting point for your triage, not a CVSS determination.
The longer table of what this audit cannot see is on the methodology page. The register of what we have missed in public is on public proof.
09 · Fit
Before the form.
We would rather tell you no at scoping than take the fee and disappoint you at week four.
Worth your time if
- You can already name the component. Most readers who get this far can.
- A failure in it costs money or trust you can put a story to.
- Your release process is settled enough to host a gate.
- A decision owner can give week one about two hours, and the component's engineers about two hours a week while we install.
Not a fit if
- You need a certified penetration test or a compliance checkbox alone. We will say so at scoping and point you to a security firm.
- There is no owner who can approve requirements for the component.
- You want total-correctness guarantees; no audit can sell those, including this one.
Stacks
Where each language stands.
The engine is language-agnostic. What differs by language is the depth of evidence we can already show you, so the table states each one.
| Language | Status | Public evidence |
|---|---|---|
| Go | Native condition-level coverage (MC/DC), measured by Proof. | jsonparser |
| C, C++ | Coverage imported from your own build: llvm-cov or gcov JSON, read into the same gate. | rsync |
| JavaScript, TypeScript | Native condition-level coverage, under node:test or Vitest. | No published depth yet |
| Rust | Native condition-level coverage. Two engines, and one of them needs a driver we have not published yet. | No published depth yet |
| Python | Native condition-level coverage, under pytest on CPython 3.12 or later. | No published depth yet |
| Java | Native condition-level coverage, under Maven or Gradle. | No published depth yet |
| C# | Native condition-level coverage, under dotnet test. |
No published depth yet |
| PHP | Native condition-level coverage, under PHPUnit. | No published depth yet |
| Zig | Native condition-level coverage, under zig build test. |
No published depth yet |
| Solidity | Native condition-level coverage, under forge test. |
No published depth yet |
| Kotlin, Ruby, Swift, Svelte | Requirements, annotations and trace links are parsed. No condition-level coverage. | No published depth yet |
| Other stacks | No condition-level engine. Line-coverage import through Cobertura, LCOV or Go profiles still satisfies the coverage gate for any language, and never the MC/DC gate. | Not applicable |
“No published depth yet” means the engine runs and we have no public corpus to point you at. That column is the honest half of this table, and it is the one that only time and published work change. Four specifics behind the rows: Rust has two engines, and the default one needs a compiler driver we have not published, built against a pinned nightly, while the in-place engine runs on stock stable; C and C++ read the coverage your own build exports, so Proof runs no build or test orchestration for them; source annotations are not parsed for C# or PHP yet; and Python measures conditions but does not yet certify the independence pairs that make coverage MC/DC, which Go does. We will tell you where each stands at scoping. Another stack? Say so on the form and you get an honest timeline.
Start
Request confidential scoping.
Pick the component you would least like to be asked about. Every request gets a reply — a scoping call or an honest no.
Confidentiality
Private by default.
We countersign your NDA before reading a line of private code. No logos, and no names in public unless you publish them.
Open source, in the open
We read the public repository. Disclosure is on your terms, and the graph can be public, as it is for jsonparser.
Read-only, on your terms
We countersign your NDA first, then read with read-only access. Nothing about the work is public unless you publish it.
Fees are quoted after scoping and fixed before work starts. We take on a small number of engagements at a time. Private code stays private. We countersign your NDA before we read a line of your code.
Prefer a call? Ask for 20 minutes →
Leonid Bugaev
founder · sets the bar, and publishes the misses from public work