Repository navigation
nvx-rs: encode what Ready reports about an activation, with conformance vectors - #874
Open
Enrique Saurez (esaurez) wants to merge 2 commits into
Conversation
Contributor
There was a problem hiding this comment.
🟢 Approval recommended
The bounded, additive implementations match the documented contracts, have comprehensive test coverage, and have no identified blocking issues.
No open issues 🎉
What changed in this PR
Completes the activation-record work in #838 by adding configuration identities and a shared Ready activation encoding for future host and guest integration. This PR adds the building blocks without changing runtime behavior.
Changes:
- Adds domain- and version-separated SHA-256 identities for canonical activation records.
- Adds strict Ready activation encoding and decoding for cold boots and clones.
- Adds conformance vectors, unit and property tests, and documentation; enables
sha2for the guest feature.
| File | Description |
|---|---|
nvx-rs/tests/vectors/README.md |
Documents the activation vector file and shared format. |
nvx-rs/tests/vectors/activation-v1.txt |
Adds record, identity, Ready, and rejection vectors. |
nvx-rs/src/tests.rs |
Exposes activation vectors to shared test helpers. |
nvx-rs/src/lib.rs |
Updates the activation module overview. |
nvx-rs/src/activation/ready/tests.rs |
Tests Ready encoding, rejection rules, and canonical round trips. |
nvx-rs/src/activation/ready.rs |
Implements the cold-boot and clone Ready codec. |
nvx-rs/src/activation/mod.rs |
Documents the contracts and adds the Ready decoding error. |
nvx-rs/src/activation/identity/tests.rs |
Tests identity vectors, field sensitivity, and Ready construction. |
nvx-rs/src/activation/identity.rs |
Implements record hashing and ReadyActivation::of. |
nvx-rs/README.md |
Documents APIs, feature requirements, and test coverage. |
nvx-rs/Cargo.toml |
Enables sha2 under the guest feature. |
doc/project-structure.md |
Adds configuration identity to the activation module description. |
Review effort: Balanced
Enrique Saurez (esaurez)
force-pushed
the
esaurez/838-pr3-configuration-identity-20261024
branch
from
October 24, 2026 19:06
746573d to
eb6087b
Compare
Enrique Saurez (esaurez)
force-pushed
the
esaurez/838-pr2-activation-encoding-20261024
branch
from
October 24, 2026 19:06
a3b2fab to
7aaa36b
Compare
This was referenced Oct 27, 2026
A host that gives a guest an activation record must learn from Ready that the guest applied it, and a clone's Ready must also name the restore that it activated, in the same encoding as a cold boot's Ready (#838). ActivationRecord::identity computes the record's ConfigurationIdentity: the SHA-256 digest of the label "nvx activation configuration identity v1", a NUL, and the record's canonical encoding. The label sets the identity apart from any other digest of the same bytes and names its version. The identity covers the whole record, a clone's restore section included, and hashes at most 1,024 bytes of settings, never an object that the record names. The guest feature now enables sha2, as the host feature does, and the identity needs one of them; the records and their encodings still need no features. ReadyActivation::of reports a record's identity and a clone's transaction ID. ReadyActivation's canonical encoding is the identity's 32 bytes, then 0 for a cold boot, or 1 and the clone's 16-byte transaction ID: COLD_LEN, 33, or CLONE_LEN, 49, bytes, which ReadyActivation::encode writes. ReadyActivation::decode refuses every other form. tests/vectors/activation-v1.txt holds conformance vectors in the line format of the other vector files: five records, from the smallest to the largest, with their identities, what Ready reports about each, 47 records and 8 Ready activations that every decoder refuses. A separate implementation of the definitions computed their bytes and identities. The tests decode and encode every vector, refuse every invalid one, check that each field changes the identity, and round-trip generated Ready activations. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> Copilot-Session: 8f7bd07b-b09f-48d5-bc49-ad06f47ef3f9
Enrique Saurez (esaurez)
force-pushed
the
esaurez/838-pr2-activation-encoding-20261024
branch
from
October 27, 2026 01:11
7aaa36b to
5edab9f
Compare
Enrique Saurez (esaurez)
force-pushed
the
esaurez/838-pr3-configuration-identity-20261024
branch
from
October 27, 2026 01:12
eb6087b to
67f6871
Compare
Ready reported a SHA-256 digest of the activation record, so that the host could learn that the guest applied exactly the record that it sent (#838). A clone's transaction ID already ties its Ready to that record: the host picks a new one for each restore and sends no other record under it. And a guest computes the digest from the bytes that it received, not from what it applied, so the digest told the host no more, at the cost of a hash on every activation, on the host and in the guest, and of sha2 in the guest. Remove ConfigurationIdentity and ActivationRecord::identity. Ready now reports that the activation applied: 0 for a cold boot, or 1 and the clone's 16-byte transaction ID, so COLD_LEN is 1 and CLONE_LEN 17. ReadyActivation::of moves beside the encoding and needs no features, and the guest feature no longer enables sha2. The record vectors lose their identities, and their tests move to the codec's tests, so they run without features. The Ready vectors hold the new encoding, and 7 Ready activations that every decoder refuses. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> Copilot-Session: 8f7bd07b-b09f-48d5-bc49-ad06f47ef3f9
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Stacked on #873; this PR retargets to dev when the pull requests below it merge. The chain on
devis #883 → #876 → #871 → #873 → #874, after #863, #864, #865, #866, #867, #868, #869, #870, #872, #875, #878, and #882, which have merged. It builds on #871's third commit, which makes the store generation a nonzerou64: the vectors give a clone's generation as a number, and refuse a generation of 0 and a short restore field.Part of #838: the last of its three pull requests. A host that gives a guest an activation record must learn from Ready that the guest applied it, and a clone's Ready must also name the restore that it activated, in the same encoding as a cold boot's Ready. This adds the canonical encoding of
ReadyActivation, which NVXC v2's Ready (#821) and the test adapter's Ready (#843) can embed, and the conformance vectors of records and of Ready's activation. It removes the configuration identity that #871 defines: Ready reports that the activation applied, and nothing hashes the record. It changes no behavior: nothing reports or checks Ready's activation yet.What changed
Ready's activation (
nvx-rs/src/activation/ready.rs).ReadyActivationholds a clone's transaction ID, or none for a cold boot, andReadyActivation::oftakes it from a record's restore section.ReadyActivation::encodewrites0for a cold boot, or1and the clone's 16-byte transaction ID:ReadyActivation::COLD_LEN, 1, orReadyActivation::CLONE_LEN, 17, bytes.ReadyActivation::decodereads them back and refuses every other form withActivationError::Ready.No configuration identity. Ready reports that the activation applied, and no digest of the record. A clone's transaction ID ties its Ready to the record of its restore, since the host picks a new transaction ID for each restore and sends no other record under it, and a guest would compute a digest from the bytes that it received, not from what it applied. So neither the host nor the guest hashes the record, and this removes
ConfigurationIdentity, which #871 defines, and its field inReadyActivation. The record'sVERSIONstays 1, since the record and its encoding don't change.Features. None. The records and both encodings need no features, so every adapter's framing can carry them, and the
guestfeature keeps its dependencies. The guest binaries, built withnvx.py build-guest-binarieson Linux x86_64, are byte-identical to those of #873's head,5edab9f, and none holds SHA-256's constants.Conformance vectors (
nvx-rs/tests/vectors/activation-v1.txt), in the line format of #727's files: five records, from the smallest to the largest of 602 bytes, cold boots and clones; what Ready reports about each of them; 47 byte strings that every decoder must refuse as a record, one for each rule; and 7 that it must refuse as Ready's activation. A separate Python implementation of the module's definitions computed their bytes, notnvx.tests/vectors/README.mdlists the file.Documentation. The module documentation defines Ready's activation and its encoding, and the crate's README describes them and the tests of the vectors.
Tests, all without features:
activation/codec/tests/vectors.rs: each record vector's values encode to its bytes, and its bytes decode to its values; every invalid record is refused;activation/ready/tests.rs: cold-boot and clone activations encode to their bytes and read back; every flag byte, and every length after it, are refused but the two forms; Ready reports each record vector's transaction ID, or none for a cold boot, in the bytes of the Ready vector of the same name; the Ready vectors and the invalid ones; and properties: generated activations round-trip, while their prefixes and longer forms are refused, and the decoder returns, never panics, and accepts only canonical encodings.Validation
At
fa45e48, on Windows and on Linux x86_64:cargo fmt --check;cargo clippywith--all-targets --all-features,--lib,--lib --no-default-features, and--lib --no-default-features --features guest, and on Linux also forx86_64-unknown-linux-musl,-D warnings;cargo testwith all, default, and no features;cargo docwith-D warnings;cargo +1.89 check;aci_edge_sandboxes' checks;bundledartifacts test, the macOS check of both crates, the guest binaries' lint, tests, build, and check, and the Markdown link check.Left to CI: the whole matrix, which runs once this pull request targets
dev.