orchestrator: add IncrementalVerifier capability trait - #30
Closed
chrysh wants to merge 8 commits into
Closed
Conversation
The PLDM firmware-device loop now notifies an UpdateEventSink once per accepted RequestUpdate, detected as the FD's only Idle -> non-Idle transition, after the success response is sent. Rejected requests (already in update mode, bad transfer size) leave the state unchanged and never notify. The sink trait stays PLDM-flavored so this crate never depends on the orchestrator stack. The mapping to Event::UpdateRequest lives in the new orchestrator-pldm-adapter crate as UpdateRequestLatch, following the same rule that keeps HAL adapters out of orchestrator-capabilities. The latch is a bool, not a counter: the FD rejects a second RequestUpdate while one is in progress, and an undrained latch across update cycles coalesces into the single UpdateRequest the state machine would act on anyway. The firmware-update host test drives the latch end to end: the accepted RequestUpdate latches exactly one Event::UpdateRequest, the duplicate is rejected with AlreadyInUpdateMode and latches nothing, and no later command in the flow latches anything. Signed-off-by: Christina Quast <christina.quast@9elements.com>
hal-adapters moves to adapters/hal and the new PLDM adapter to adapters/pldm, so the growing family of producer-to-orchestrator adapter crates (HAL, PLDM, later SPDM) sits under one directory. Crate and target names are unchanged; each adapter keeps its own crate so composing one stack never pulls in another. Signed-off-by: Christina Quast <christina.quast@9elements.com>
More PLDM lifecycle events are coming (cancel, transfer/verify/apply complete, activate). Replace UpdateEventSink's per-event method with a non_exhaustive FdEvent enum and a single FdEventSink::notify, so new events are one variant instead of a trait break. Every variant payload stays Copy and lifetime-free: across the DSP0267 FD surface the orchestrator-relevant edges carry only small integers; buffer-shaped data (image chunks, package data, version strings) lands behind FdOps and events name it instead of carrying it. UpdateRequested is the only variant for now. The adapter latch keeps its semantics and drops unmapped events. Signed-off-by: Christina Quast <christina.quast@9elements.com>
Clippy's single_match lint (denied under -D warnings in presubmit) rejects a one-arm match with a wildcard. FdEvent derives no PartialEq, so use matches! rather than an equality check. Signed-off-by: Christina Quast <christina.quast@9elements.com>
The four Effect::Report* variants had no consumer seam. Add a non_exhaustive Report enum and one ReportSink::report, not a method or a trait per variant, plus a unit impl for a board with no management side to tell. report returns nothing: an error channel would put reports on the driver's fail-closed path, letting the act of reporting a contained failure escalate it. Trait only, composing a sink into the board follows. Assisted-by: Claude:claude-opus-5 Signed-off-by: Christina Quast <christina.quast@9elements.com>
Ready now means the staged payload is verified to the archetype's discipline: a direct-flash adapter reads written pages back before reporting Ready, a PLDM device runs its own verify step after the transfer. This drops the planned ReadBack capability; a separate post-Ready check would leak archetype knowledge to the caller and PLDM devices cannot serve it at all. The commit bullet now points at the BootConfirmed gated flow instead of a TrialBoot capability. UpdateError gains ReadbackMismatch. Folding it into Device would hide the one device fault a caller can act on differently: the write path reported success and the storage still disagrees, so a slot that keeps mismatching is worth retiring rather than retrying. MockFlashDevice demonstrates the discipline: writes hold written still, readback advances it, and a mismatch fails the step. MockPldmDevice takes a verify step of its own once the transfer completes, so a finished transfer is not yet Ready. Assisted-by: Claude (Fable 5) Signed-off-by: Christina Quast <christina.quast@9elements.com>
SvnFloor joins BoardCapabilities, one floor per component slot. The SVN to advance to travels in Verdict::Authenticated: verification is the only authenticated read of the manifest, so nothing else may tell the floor where to go. The driver caches it per component, clears it on rejection, and fails closed when asked to commit without it. SvnFloorBinding names the two wirings a board can choose: Erot, where the eRoT holds the floor, and SelfManaged for a component that tracks its own SVN (iRoT, or a PLDM device committing internally), whose commit is a no-op. Assisted-by: Claude:claude-fable-5 Signed-off-by: Christina Quast <christina.quast@9elements.com>
Polled incremental verification seam for the update path: judge a candidate image one bounded step at a time so the single-threaded runtime stays live while hashing megabytes of payload. The trait lives in orchestrator-capabilities (dependency-free leaf). start() opens a session, poll(payload) does one implementor-chosen chunk of work and returns Processing/Authenticated/Rejected. Faults (unreadable payload, crypto error, misuse) are Err, never a verdict, so a check that could not run cannot forge a judgment. After an Err the session is abandoned; only start() restores defined state. Explicit start() (unlike Updatable's implicit idle-to-active) catches an accidental extra poll after a verdict instead of silently re-hashing from zero. Assisted-by: Claude
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.
Summary
Trait-only PR. Adds
IncrementalVerifiertoorchestrator-capabilities:polled, chunked image verification so the update pump never blocks on
hashing megabytes of payload. Same poll-not-block contract as
Updatable.Driver composition (the adapter that wraps a crypto backend behind this
trait, wired into the update pump) follows in a stacked PR.
Effect::AuthenticateUpdateremains stubbed in the SM until then.Naming decisions for review
VerifyStepvs the sibling'sStageProgress: worth mirroring asVerifyProgress?Processing { hashed, total }lands ahead of the update-pump plan'sProgressnewtype (step 1). If the newtype arrives later, this varianttakes a shape break. Also
hashedvs the plan'sdone.update-pump-design.mdneeds a line edit after this lands.Assisted-by: Claude