Skip to content

nvx-rs: encode what Ready reports about an activation, with conformance vectors - #874

Open
Enrique Saurez (esaurez) wants to merge 2 commits into
esaurez/838-pr2-activation-encoding-20261024from
esaurez/838-pr3-configuration-identity-20261024
Open

Enrique Saurez (esaurez) wants to merge 2 commits into
esaurez/838-pr2-activation-encoding-20261024from
esaurez/838-pr3-configuration-identity-20261024

Conversation

@esaurez

@esaurez Enrique Saurez (esaurez) commented Oct 24, 2026 •

Copy link
Copy Markdown
Contributor

Stacked on #873; this PR retargets to dev when the pull requests below it merge. The chain on dev is #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 nonzero u64: 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). ReadyActivation holds a clone's transaction ID, or none for a cold boot, and ReadyActivation::of takes it from a record's restore section. ReadyActivation::encode writes 0 for a cold boot, or 1 and the clone's 16-byte transaction ID: ReadyActivation::COLD_LEN, 1, or ReadyActivation::CLONE_LEN, 17, bytes. ReadyActivation::decode reads them back and refuses every other form with ActivationError::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 in ReadyActivation. The record's VERSION stays 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 guest feature keeps its dependencies. The guest binaries, built with nvx.py build-guest-binaries on 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, not nvx. tests/vectors/README.md lists 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 clippy with --all-targets --all-features, --lib, --lib --no-default-features, and --lib --no-default-features --features guest, and on Linux also for x86_64-unknown-linux-musl, -D warnings; cargo test with all, default, and no features; cargo doc with -D warnings; cargo +1.89 check;
  • the runtime adapter's protocol-only and host-only configurations, and, on Linux, its guest-only configuration;
  • aci_edge_sandboxes' checks;
  • on Linux, also the bundled artifacts 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.

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟢 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 sha2 for 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

@esaurez
Enrique Saurez (esaurez) force-pushed the esaurez/838-pr3-configuration-identity-20261024 branch from 746573d to eb6087b Compare October 24, 2026 19:06
@esaurez
Enrique Saurez (esaurez) force-pushed the esaurez/838-pr2-activation-encoding-20261024 branch from a3b2fab to 7aaa36b Compare October 24, 2026 19:06
@esaurez
Enrique Saurez (esaurez) requested a balanced review from Copilot October 24, 2026 19:06

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟢 Approval recommended

The additive APIs match the specified identity and encoding contracts, with comprehensive targeted coverage and no identified blocking issues.

No open issues 🎉

Review effort: Balanced

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

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟢 Approval recommended

The bounded hashing and strict codec implementations match the documented contract, with comprehensive coverage and no unresolved blocking findings.

No open issues 🎉

Review effort: Balanced

Comment thread nvx-rs/src/activation/identity.rs Outdated
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
@esaurez Enrique Saurez (esaurez) changed the title nvx-rs: identify activation configurations and encode Ready's activation nvx-rs: encode what Ready reports about an activation, with conformance vectors Oct 27, 2026
@esaurez
Enrique Saurez (esaurez) requested a balanced review from Copilot October 27, 2026 03:45

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟢 Approval recommended

The bounded codec matches the specified wire forms, with conformance and property coverage and no identified blocking issues.

No open issues 🎉

Review effort: Balanced

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants