Should the reproduction record be an open format?

Written 1 September 2026. This is a design document. Nothing in it was built, and the recommendation at the end is that most of it should not be.

Every statement about this codebase names the file and line that proves it and was checked against that file. Every statement about prior art names a URL and says how many sources it rests on and whether the primary document was read or only a search summary. Where something could not be verified in this pass it is marked unverified, which is a finding.

The engine agrees with P6 on 67.85% of 584,687 comparisons across the held-out corpus (engine/oracle/README.md, tier f). Nothing in this document makes that number better, and a verification format that appeared to would be the exact failure this project guards against hardest. The reader should hold that figure in mind through the whole of section 4, because it is the reason the most interesting idea here is not a verification format at all.


1. The answer, first

No. Do not write a specification.

There is a smaller thing that is worth doing, it is about a fifth of a day's work, and it is not a standard. Publish the answer table — the fifteen columns cpmcore already freezes in ROW_KEYS — as a documented, versioned artefact, together with the mapping from each column to the field a P6 XER already stores for it. That mapping already exists in this repository, at engine/oracle/harness.py:156-166, and it is the only part of the whole apparatus that lets somebody check us without running our code and without writing a scheduler.

Everything else — a wrapper format, a schema language, a second implementation, an AACE submission — fails one of three tests: it is already covered by something published (section 5), it requires the checker to become a competitor (section 4), or it costs a maintained specification forever in exchange for readers who do not exist yet (section 7).

The rest of this document is the working.


2. What is actually attested today

A record is a set of claims. There are four in ours and they are not equally strong, equally portable, or equally checked.

The four claims

One: these bytes. Provenance.file_digest, a SHA-256 over the input as received (evidence.py::digest_file, streaming, opened "rb"). This is the FRE 902(14) custody claim. It is also the one claim that is platform-dependent, because core.autocrlf changes the bytes of a schedule file that passes through git — measured, with both digests printed, in REPRODUCIBILITY.md §3. verify_record reports a difference here as a warning, naming line-ending translation as the ordinary explanation (evidence.py:1135-1144).

Two: parsed this way. Provenance.model_digest, over the sorted canonical form of tasks, links and calendars plus the data date (evidence.py:283-290). Reported as an error on difference, ahead of the dates, so a reviewer sees one cause rather than a thousand consequences.

Three: under these options. The manifest carries options and calendars (ReproducibilityManifest, evidence.py:723-726), and the class docstring states the governing rule: record what was used, never what was defaulted — options read off the computed result rather than off what a caller intended to pass (evidence.py:802-812).

Four: produced these dates and floats. answer_digest over answer_of (evidence.py:825-884): the summary, and one row per activity sorted by activity id. This is the claim that did not exist until this week and it is the whole ballgame; REPRODUCIBILITY.md §4 records that it was absent everywhere.

What is deliberately excluded, and the exclusions are right

The traversal order, because two topological orders can be equally valid for one network and digesting one would fail a reproduction over something that is not a disagreement about any date — and where the traversal is load-bearing it is covered anyway through summary()["longest_path"], which is order-significant and is exactly where an order-dependent tie-break surfaced under mutation (REPRODUCIBILITY.md §1). The issue log, because import warnings are diagnostics about the file and their wording changes when a message improves. The report, because Report.prepared is date.today().

I checked the second exclusion for a consequence the documents do not draw, and found one; it is in section 8 below. The exclusions are still right.

Which of the four a second implementation could check

This is the question that decides whether an open format is possible, and the answer is not uniform across the four.

claim what a second implementation needs portable?
these bytes SHA-256 yes, trivially
parsed this way our exact data model, field for field no
under these options a name-value comparison yes, and it is already inside claim four
produced these dates a comparison of flat scalars yes

The second row is decisive and it is a fact about the code, not an opinion. _canonical reduces a dataclass by walking fields(value) and keeping those with f.compare true (evidence.py:195-198). So model_digest is a function of our class definitions — the names of cpmcore dataclass fields and which of them are marked compare=False. A second implementation cannot recompute it without reimplementing our data model exactly, and the moment a schedule file contains a field we model and they do not, or vice versa, the digests part with no defect on either side.

That means: the model digest is engine-specific by construction, and it is currently the claim verify treats as an error. An open format would either have to drop it, or specify our internal representation in full — which is a far larger document than a record format and would freeze the data model against every future importer fix.

Claims one and four are portable. Claim three turns out to be portable and already covered: ScheduleOutcome.summary() includes "options": self.options.to_dict() (schedule.py::ScheduleOutcome.summary), so the options as applied are inside the digested answer and a difference in them fires REPRO.ANSWER.SUMMARY, not merely a mismatch of an unread manifest field.


3. Where it stops being verifiable

REPRODUCIBILITY.md §6 already gives the honest list and I am not going to improve on it: the input file may not be the one the contractor submitted; the record may not predate the dispute; the engine may be wrong, in which case two runs of wrong code agree and the verifier prints REPRODUCED; the parties may not have run the same engine; and the analysis may answer the wrong question.

Three things a format changes about that list, and one it does not.

A format makes the limits carryable. Today those five limits live in a markdown file in our repository. A reviewer who receives a record receives no statement of them at all. The single most valuable line any format could carry is a limits field naming what the record does not establish, because an opposing expert reading a JSON blob has no reason to know that the answer digest says nothing about correctness. This costs one string and no maintenance.

A format that hides a limit is worse than none. Any wrapper with a top-level verified: true would be that. The engine already refuses this shape once, on purpose: Certification.to_dict reports "signed": False unconditionally and the comment says no code path in the engine may set it otherwise (evidence.py::Certification.to_dict). The same discipline has to govern a format's vocabulary. REPRODUCED is a good word precisely because it does not mean correct.

A format cannot fix the timestamp, and should stop trying. The decision in REPRODUCIBILITY.md §6 — no RFC 3161 client, a documented procedure the analyst runs with openssl and ots — is right, holds under dependencies = [], and is unaffected by anything here. A format's contribution is a place to record the token, which Timestamp already is (evidence.py:584-636). The two caveats stand: no TSA has been contacted from this tree, and no command builds a Ledger, so the token is filed beside the record rather than sealed into a chain.

And the third limit is untouched, permanently. At 67.85% agreement with P6, reproduction is agreement between two runs of code that disagrees with Primavera on roughly one field in three. A verification format applied to that is a precise record of a disputed answer. That is a genuinely useful thing to be — but only if the format says so on its face.


4. What a second implementation would need — the crux

The brief puts the crux correctly: verifying that the same dates come out requires computing the dates, and at that point the verifier has written a CPM engine and is a competitor rather than a checker. The three products named in the brief are the right decomposition, so take them one at a time.

Verifying the inputs were as stated needs only a parser. True, and it is worth almost nothing. It establishes "we both read the same file", which REPRODUCIBILITY.md §4 correctly calls the claim the record could support before the answer digest existed and describes as the gap that was the whole ballgame. Nobody will build a parser to re-derive a claim that weak. And as section 2 showed, the model digest — the interesting half of "the inputs were as stated" — is not reproducible by a second implementation at all.

Verifying the answer is correct needs a scheduler. True, and this is the product nobody will build, for a reason sharper than effort: an opposing expert who has written a CPM engine has no reason to check ours against theirs rather than simply asserting theirs. The asymmetry that makes reproducible builds work — many rebuilders, one canonical artefact, and rebuilding is cheap and uninteresting — does not hold here. Rebuilding a Debian package is a chore; building a scheduler is a business.

Verifying the answer against a stated answer needs only a comparison. This is the middle product and the brief is right that it may be the whole idea. But it has a hole in it as stated, and finding the hole is where the useful part came from.

A comparison needs two answers. If the second one comes from re-running our engine, the reviewer is back to trusting our code. So the middle product is only worth something if the second answer comes from somewhere the reviewer already trusts.

It does. It is in the file.

engine/oracle/README.md opens with the sentence this whole document turns on: "an XER exported from P6 already contains P6's answers. We do not need to run P6. We need files P6 has already run." Every XER carries early_start_date, early_end_date, late_start_date, late_end_date, total_float_hr_cnt and free_float_hr_cnt on its TASK rows — Primavera's own computed values, stored by the tool the opposing expert already owns and already believes.

So the engine-independent check available to an opposing expert today, with no scheduler and no parser beyond one they can write in an afternoon, is:

Take our stated answer table. Take the corresponding fields off the TASK rows of the XER they gave us. Compare, activity by activity, field by field.

No trust in us, no CPM implementation, and the reference implementation is Primavera. The field mapping is already written down, with its per-field caveats, at engine/oracle/harness.py:156-166 — including that early_start_date and early_end_date are P6's forecast dates except on finished rows, which is the sort of detail that makes an unguided comparison produce nonsense.

And now the honest part, which is why this is a disclosure and not a triumph. Run that comparison and roughly one field in three will differ, because that is what 67.85% means. A reviewer doing it will find hundreds of divergences. Our own harness finds them; that is what tier (f) is.

I think that is a feature and I want to be careful about why, because the temptation to spin it is exactly the failure mode CLAUDE.md records. It is not a feature because disagreement is good. It is a feature because the disagreements are itemised, located and disclosed by us rather than discovered by them, and because a schedule of differences between our answer and the opposing party's own P6 export is precisely the document a tribunal needs and that no incumbent produces. The alternative is not "an analysis nobody can fault". The alternative is an analysis nobody can check, which is what the entire rest of the category ships.

It is also, plainly, a thing that could be used against us, and any decision to publish it has to be taken with that in the open rather than discovered later.

This is a different artefact from a verification format. It is a differential disclosure, most of it is already built in engine/oracle/differential/, and it does not need a specification — it needs one page saying which of our columns lines up against which of P6's fields and under what conditions. That page is the recommendation in section 9.


5. Prior art — and there is enough of it

Searched 1 September 2026. Where I read only a search summary rather than the primary document I say so, because "a specification says X" sourced from a search snippet is exactly the kind of sentence this project has been burned by.

The software supply-chain world has solved the wrapper

in-toto Attestation Framework. A Statement is four fields: _type, always https://in-toto.io/Statement/v1; subject, an array of artifacts each with a name and a digest map; predicateType, a URI naming what kind of claim this is; and predicate, an object whose schema that URI defines. The envelope and signature are explicitly a separate layer outside the Statement spec. Primary document fetched: github.com/in-toto/attestation/blob/main/spec/v1/statement.md (one source, read directly).

That is our record, exactly. subject is the input files with their file_digests; predicateType is a URI we own; predicate is the manifest and the answer. Adopting it costs a constant string and an array rename. It is plain JSON — no library, no crypto, nothing that touches dependencies = [], because the signature layer we are declining anyway.

SLSA provenance (slsa.dev/spec/v0.1/provenance, one source, search summary only) is a predicate type for builds, in the same framework. Not a fit for a schedule analysis, and no reason to force it. The lesson is the pattern: SLSA did not invent a wrapper, it defined a predicate inside somebody else's.

Reproducible Builds (reproducible-builds.org, plus github.com/kpcyrd/ rebuilderd, two sources, search summaries only) is the closest conceptual relative and the most useful negative result. Its infrastructure — rebuilderd splitting work among independent rebuilders, GOOD/BAD/UNKWN status, historic attestations retained, over 150,000 attestation reports from 20 independent builders in the Nix/Guix Lila project — exists because many parties independently want to rebuild the same artefact cheaply. Section 4 explains why that condition does not hold for delay analysis. The analogy that inspired this idea is the analogy that argues against it.

C2PA / Content Credentials (spec.c2pa.org, version 2.2 dated 2025-05-01, one source, search summary only). Manifest of assertions, a required hard binding which is a cryptographic hash of the asset, claim signatures, and redaction rules that forbid redacting the hard binding. Structurally the nearest thing to what a construction-evidence format would be, and it required a consortium and years. Worth citing to a tribunal as the shape the wider world has converged on; not worth imitating in scope.

RFC 8785, the JSON Canonicalization Scheme (datatracker.ietf.org/doc/rfc8785 and rfc-editor.org/info/rfc8785, two sources, search summaries only). Sorted properties, ECMAScript number serialisation, whitespace removed. Note the status, which matters if it is ever cited in an expert report: it is an Independent Submission, not endorsed by the IETF and with no standing in the standards process.

We do not implement JCS. canonical_json is json.dumps(sort_keys=True, ensure_ascii=True, separators=(",",":")) (evidence.py:218, 221-229), which differs from JCS in at least two nameable ways: ensure_ascii=True escapes non-ASCII as \uXXXX where JCS mandates UTF-8 with minimal escaping, and Python sorts keys by Unicode code point where JCS sorts by UTF-16 code unit, which diverges for characters above the Basic Multilingual Plane. I did not measure whether any file in the corpus contains such a character, so I state the divergence and not its consequence.

For the answer table the divergence is close to irrelevant, because the rows are activity ids, ISO date strings, integers and booleans. For the model digest it is live, since activity names go into it. That asymmetry is one more reason the answer table is the portable artefact and the model digest is not.

RFC 3161 timestamping. Already assessed and already decided in REPRODUCIBILITY.md §6, on the correct ground. Nothing here reopens it.

AACE RP 29R-03. Searched three secondary sources — the published table of contents at web.aacei.org/docs/default-source/toc/toc_29r-03.pdf, Long International's method summary, and Ankura's 2025 piece harmonising the RP with the SCL Protocol. Its §2 Source Validation Protocols (SVP 2.1 through 2.4) are about schedule validation — baseline selection, as-built reconstruction, update validation, delay-event identification — and nothing found mentions cryptographic authentication, hashing, or re-running an analysis. Recorded as "none found in the sources searched", not as "none exists": I did not read the full RP, which is behind AACE membership, and this repository's own citations of it were made from the document rather than from search.

SCL Delay and Disruption Protocol, 2nd edition, February 2017 (scl.org.uk/sites/default/files/documents/SCL_Delay_Protocol_2nd_Edition_Final.pdf, one source, search summary only). Concerned with records and with transmitting information in native format, and with the parties agreeing a protocol for it at the outset. That is an adoption hook — a contract clause is a place a record requirement could live — and it is not a verification format.

FRE 902(13) and (14) are already handled better in evidence.py:1342-1450 than a new format would handle them, including the two limits that get lost in the enthusiasm: self-authentication is not a hearsay answer, and Rule 902(11)'s written-notice requirement is forfeitable by omission.

The conclusion from prior art

Adequate prior art exists for the wrapper and does not exist for the content. Nobody needs to invent a way to say "this attestation is about these artefacts and makes this kind of claim" — in-toto did that, in four fields, in plain JSON. What nobody has done is define the claim for a CPM schedule analysis. That is a predicate type, not a format, and a predicate type is a page.


6. Who would adopt it, and why they would not

Four candidate populations. I have talked to none of them; this is reasoning from the sources in docs/POSITIONING.md and outreach/, and it should be read as reasoning.

Opposing experts. The intended audience. They would not adopt a format; at most they would run one command once, in one dispute, if their client's counsel told them to. That is a fine outcome and it needs no standard — it needs a verifier they can read, which evidence.py already is by deliberate design (REPRODUCIBILITY.md §5: a hundred readable lines at the bottom of the module that defines the record, reachable with a plain python -m).

Owners and agencies writing schedule specifications. The realistic adopter, because a spec clause is where a submission requirement can be made mandatory, and this project is already reading VDOT's P6 settings. But what an agency would mandate is a submission requirement — hand over the native file and its hash — not a verification format. The thing that would get adopted is one sentence, and it is a sentence about custody, which is claim one, the trivially portable one.

Other tool vendors. Would not adopt a format published by a competitor with one implementation. docs/POSITIONING.md records that Schedule Analyzer, the tool this most resembles, closed after 28 years; the survivors are priced from $344 to $25,000 a year and none of them publishes a reproducible record. A format that invites a customer to check the vendor's arithmetic is against every incumbent's interest, and that is not cynicism, it is the reason the category looks the way it does.

AACE. The most interesting and the least likely on any short horizon. The route exists — AACE publishes recommended practices, they are written by working groups of practitioners, and 29R-03 §2 is squarely about source validation. The route is also slow, requires being a known contributor before being an author, and 29R-03 itself dates from 2003 with a 2011 revision. My honest estimate of the odds that a document originating here becomes an AACE RP within three years is low — I would not put it above one in ten — and it is a bad reason to write a specification now, because the RP that eventually gets written would be written by a committee from scratch regardless of what we published.

There is a much better version of the AACE route and it is not a format. It is a finding: a short paper reporting that an independent CPM implementation agrees with P6 on 67.85% of 584,687 field comparisons across 68 real exports, with the divergence classes named. That is new empirical knowledge about the tool the entire field depends on, nobody has published it, and it is the kind of thing a recommended practice cites. It also costs no maintained artefact.


7. The case against, at full strength

Stated as strongly as I can make it, because a design document that only argues its own side is worth nothing.

This is a solution looking for a problem. No opposing expert has ever asked for it. Nobody in construction scheduling has asked for it, and the reason is not that the field has not thought of it — it is that the field settles delay claims by negotiation on the courthouse steps, where the currency is the reputation of the expert and the appetite of the parties, not the checkability of the arithmetic. An expert who says "here, check my working" is not read as candid; they are read as inexperienced. The senior people in this field have built careers on being believed.

A format is a permanent liability. A file layout has one implementation and can change on Tuesday. A specification acquires readers who encode assumptions about it, and the moment a second party writes anything against it, every future change to ROW_KEYS or CANONICAL_SCHEMA becomes a compatibility question rather than a commit. This repository has one maintainer. CANONICAL_SCHEMA went 1 to 2 this week for a good reason, and a published format makes the next such fix cost a version negotiation.

And the timing is wrong in the worst possible way. Publishing a format whose central promise is "check us" while the engine agrees with P6 on 67.85% of comparisons is an invitation to be checked and found wanting, in public, in the one artefact that would carry our name furthest. The correct order is: get the number up, then invite scrutiny.

The response

The first paragraph I mostly accept, and it is why the recommendation is not a standard. It is wrong in one place: the buyer for checkability is not the opposing expert, it is counsel instructing the expert, and counsel's incentive is exactly the opposite — a testifying expert whose method survives a Daubert challenge is worth more than one who is merely believed, and reproducibility is the one Daubert factor a software vendor can simply satisfy rather than argue about, which ReproducibilityManifest's own docstring already says (evidence.py:694-699).

The second paragraph is correct and is the reason the recommendation is a document about an existing artefact rather than a new artefact. ROW_KEYS is already frozen with a test behind it (schedule.py:79-81), and CANONICAL_SCHEMA already exists to make an old digest unable to compare equal to a new one. Documenting what is already pinned adds no new commitment. Writing a specification would.

The third paragraph is the one I want to reject and cannot fully. It is right that publishing invites scrutiny. It is wrong that the order should be reversed, for the reason CLAUDE.md states as a standing rule: the moment agreement becomes a target it stops measuring. "Get the number up, then publish" is that rule violated on a longer timescale. But the paragraph survives in a weaker and still real form: the disclosure in section 4 is a decision with a downside, and it is Charley's to take, not a technical detail to be shipped inside a recommendation.


8. Two findings in the code, and one is smaller than it looked

I was asked to name it if the code contradicts REPRODUCIBILITY.md. Two things turned up. The first is real and small; the second is a documentation imprecision that I nearly reported as a hole, and the correction is worth more than the finding.

Finding one: --project is an input to the analysis and no manifest records it

Closed 2026-09-02, and this section is kept as the record of why. Both recorders now write method.project where a selector was given (evidence._method), python -m forensic.evidence verify takes --project and passes it, and verify_record reports REPRO.METHOD.PROJECT as a warning before the digests, so the misdiagnosis described below no longer happens. The gap the rest of this section describes is the state before that change; the finding is not open.

The wider version of it was not closed at the same time and was found separately: the verifier read method.project and nothing else in the manifest at all — see quality/THREAT-MODEL.md N5, closed 2026-09-02 by naming every unchecked method field, verifying the manifest's own digest against its body, and narrowing the sentence the command prints.

construct record --project X selects which project inside a multi-project XER is imported, which changes the tasks, the model digest and every date. The manifest's method for that path records only the command and the jurisdiction (cli.py::_record_cmd); the standalone recorder's records only the command and the file names (evidence.py::main). Neither records --project.

The consequence is concrete. python -m forensic.evidence verify re-loads through _load(Path(path)) with no project selector (evidence.py:1487), and _read_project with requested=None on a multi-project file warns and imports the first project (xer.py:1058-1067). So the reproduction reads a different network, and verify correctly fails with REPRO.INPUT.MODEL_DIGEST and a flood of field differences.

It fails safe, which is the important half. But it fails with a misdiagnosis: the finding says "the two sides read different networks from these files", the reviewer has no way to learn that an unrecorded argument is the cause, and the one channel that would have told them — XER.PROJECT.MULTIPLE — is in the issue log, which is deliberately outside the answer. This is the same class as the V4 finding in THREAT-MODEL.md §8: not a false REPRODUCED, a divergence pointing at the wrong thing.

REPRODUCIBILITY.md does not claim --project is recorded, so this is a gap rather than a contradiction. It is worth closing because it is one key in method, and because "argument order is itself an input" is already a sentence the verifier prints (evidence.py::verify_record) — the document knows arguments are inputs and two named ones are missing.

I also checked --baseline and it is not affected: Submission.latest is max by data date (rules/__init__.py:190-192), independent of which snapshot is marked baseline, so --baseline changes the findings in the report and not the answer that verify compares. Recorded because I expected the opposite and was wrong.

Finding two: the standalone recorder writes empty options and calendars

python -m forensic.evidence record — the command REPRODUCIBILITY.md §5 names first — builds its manifest with options={} and calendars={} (evidence.py::main). Only construct record --json goes through manifest_for and gets the real ones (cli.py::_record_cmd). So ReproducibilityManifest's governing rule — record what was used, calendars in full by definition rather than by name — is not honoured on one of its two producers, and §6's sentence that manifest.digest "commits to the inputs, the scheduler options as applied, the calendars in full, the method" is, read literally against that path, inaccurate.

And it matters much less than that paragraph implies, which is the finding. Both are committed to transitively. The calendars are inside every input's model_digest (evidence.py:283-290, called with snapshot.calendars at evidence.py:1487), which verify checks as an error. The options are inside the answer, because ScheduleOutcome.summary() carries "options": self.options.to_dict() (schedule.py::ScheduleOutcome.summary) and answer_of canonicalises the summary — so an options difference fires REPRO.ANSWER.SUMMARY, a localised finding, not a silent pass. manifest.digest covers both inputs and answer_digest, so a timestamp over it does commit to the calendars and the options.

So: a documentation precision issue about mechanism, not a gap in coverage. I am recording it in that form deliberately. The overstated version — "the record does not commit to the calendars" — was the sentence I had written before I traced it, it would have been false, and it would have sat under a true-sounding heading, which is the failure CLAUDE.md names twice.


9. The smallest first version that would be worth anything to somebody else

One document and two small code changes. Not a specification, not a schema language, not a second implementation, and no dependency.

The document — docs/ANSWER-TABLE.md, about two pages. It states:

Code change one: wrap the record in an in-toto v1 Statement. Four fields, one constant, subject from the provenance list, predicateType a URI we own, predicate the existing {manifest, answer} object. _as_record already unwraps two shapes (evidence.py:1497); this is a third, and it costs a handful of lines. The gain is that the record stops being a private layout and becomes an instance of a format that supply-chain tooling, and more importantly a cross-examining barrister's technical adviser, can look up. Do this only if the document above gets written; on its own it is decoration.

Code change two: put project in method. One key, closing finding one.

What is explicitly not in the first version. No JSON Schema — it would be a dependency at validation time and the document is more precise than the schema would be. No signature layer. No verified boolean anywhere. No second implementation, and no encouragement of one, because section 2 shows the model digest cannot be reimplemented and section 4 shows nobody will build the scheduler. No AACE submission; if anything goes to AACE it should be the empirical finding from section 6, not a format.

How to tell whether it was worth it. One test, and it is a person and not a suite: hand the document and one record to somebody who has P6, is not us, and does not like us, and see whether they can produce a schedule of differences against their own export without asking a question. If they can, the middle product exists. If they cannot, the document is wrong and no specification would have saved it.


10. Summary

Attested today: the input bytes, our parse, the options as applied, and every computed date, float and flag — the last of these being new this week and the one that matters. Not attested, and not attestable by any format: that the file is the one submitted, that the record predates the dispute, and that the arithmetic is right.

Adequate prior art exists for the wrapper. in-toto's Statement is our record in four fields and costs nothing to adopt. Nothing in the construction or legal-evidence world does this job, in three secondary sources searched, and that is recorded as none found rather than none existing.

The weaker-but-useful claim is real and it is not the one the brief expected. It is not "check our answer against a stated answer" — that needs a second answer from somewhere trustworthy. It is check our answer against the answers P6 already wrote into the file, which needs no scheduler, no trust in us, and a mapping table this repository already contains. It will disagree about two fields in five, and disclosing that ourselves is the point.

Who would adopt a format: essentially nobody, on any timescale worth planning against. What would get used: one command, once, in one dispute, by an expert told to run it — which needs a readable verifier, which exists.

Is it worth building? The specification is not. The two-page document describing what is already frozen, plus the P6 mapping, is — it is a fifth of a day, it commits us to nothing new, and it is the only version of this idea that somebody other than us could use tomorrow.

Source: docs/VERIFICATION-FORMAT.md. Source commit date: 2026-09-06.

See it in practice

Follow the evidence, from the schedule to the finding.

Explore the worked example