Skip to content

Fix DPU firmware update health alert never clearing on DPF hosts - #4236

Merged
wminckler merged 1 commit into
NVIDIA:mainfrom
wminckler:fix/dpf-firmware-update-health-alert
Jul 28, 2026
Merged

Fix DPU firmware update health alert never clearing on DPF hosts#4236
wminckler merged 1 commit into
NVIDIA:mainfrom
wminckler:fix/dpf-firmware-update-health-alert

Conversation

@wminckler

Copy link
Copy Markdown
Contributor

DPF-ingested hosts never had their HostUpdateInProgress health alert removed after an automatic DPU firmware update finished. The machine would reprovision successfully, come back Ready, and then sit permanently with an AutomaticDpuFirmwareUpdate alert pinned to it. Non-DPF hosts were unaffected.

The cause is an asymmetry between how an update is started and how it is completed. DPF hosts are deliberately excluded from the version-based staleness check — find_outdated_dpus returns early for any host with dpf.used_for_ingestion, and find_outdated_dpus_dpf selects those hosts instead by comparing against the expected BFB from their DPUDeployment. The completion path had no such split: it only removed the update markers when the DPU's reported NIC firmware appeared in dpu_nic_firmware_update_versions, a config list that only ever contains NIC firmware version strings. Nothing in the DPF path constrains a DPU to land on a version from that list, so for a DPF host the comparison had no reason to ever match, and the marker was never removed.

The consequences went beyond a stale alert. The alert carries prevent_allocations, so affected hosts stayed unallocatable indefinitely. The lingering alert also makes is_available_for_updates return false, which excluded those hosts from every subsequent firmware update. And each manager pass emitted a spurious WrongVersionAfterUpdate failure metric for a host that had in fact updated correctly.

The fix carries the host's DPF-ingestion flag through DpuMachineUpdate so the completion path can mirror the split the start path already has, skipping the NIC-version comparison for DPF hosts. The rest of the completion gate is untouched: the host must still be holding the update marker, be in ManagedHostState::Ready, and have every one of its DPUs' reprovisioning_requested flags cleared before anything is removed.

Related issues

None.

Type of Change

  • Add - New feature or capability
  • Change - Changes in existing functionality
  • Fix - Bug fixes
  • Remove - Removed features or deprecated functionality
  • Internal - Internal changes (refactoring, tests, docs, etc.)

Breaking Changes

  • This PR contains breaking changes

Testing

  • Unit tests added/updated
  • Integration tests added/updated
  • Manual testing performed
  • No testing required (docs, internal refactor, etc.)

Added test_clear_completed_updates_dpf_host_off_list_version, which marks a host DPF-ingested, lands its DPU on a firmware version asserted to be absent from dpu_nic_firmware_update_versions, clears the reprovisioning flag, and leaves the update marker in place. It asserts the health report is removed, aggregate health is clean, and no wrong_version_after_update failure is counted. The test fails against the previous behaviour.

Ran the dpu_nic_firmware (7 tests), dpu_machine_update, and machine_update_manager (18 tests) suites — all passing. Not yet exercised against a live DPF-managed cluster.

Additional Notes

DpuMachineUpdate::dpf_managed is marked #[sqlx(default)] because the struct is also loaded via FromRow in get_reprovisioning_machines, whose query does not select the column; that path only consumes host_machine_id, so defaulting to false there is inert.

Worth a reviewer's opinion: when a DPF host's reprovision completes but the DPU is still mismatched against a DPUDeployment that changed mid-update, this clears the marker rather than retaining it. That is deliberate — run_single_iteration calls clear_completed_updates and then start_updates in the same pass, so the host is re-detected by find_outdated_dpus_dpf and the update is re-triggered immediately, with the marker re-applied. Retaining the marker instead would make is_available_for_updates false forever and recreate exactly the permanent-pin failure this PR fixes.

🤖 Generated with Claude Code

DPF-ingested hosts pick their DPU firmware update targets from the
DPUDeployment's expected BFB — find_outdated_dpus skips DPF hosts
outright and find_outdated_dpus_dpf selects them by BFB hash instead.
The completion path, though, only removed the update markers when the
DPU's reported NIC firmware appeared in dpu_nic_firmware_update_versions,
a list that only ever holds NIC firmware strings. For a DPF host that
comparison has no reason to match, so a successful reprovision left the
HostUpdateInProgress alert pinned on the host forever.

Because that alert carries prevent_allocations, the host stayed
unallocatable, and its lingering alert also made is_available_for_updates
return false, excluding the host from every later firmware update. Each
manager pass additionally emitted a bogus WrongVersionAfterUpdate
outcome.

Carry the host's DPF-ingestion flag through DpuMachineUpdate so the
completion path can skip the NIC-version comparison for DPF hosts. The
rest of the completion gate is unchanged: the host must still hold the
update marker, be Ready, and have every DPU's reprovisioning flag
cleared.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@wminckler
wminckler requested a review from a team as a code owner July 28, 2026 14:21
@coderabbitai

coderabbitai Bot commented Jul 28, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: f79dd42b-3014-4126-8f67-972c08604660

📥 Commits

Reviewing files that changed from the base of the PR and between 858c158 and 7ba222e.

📒 Files selected for processing (7)
  • crates/api-core/src/machine_update_manager/dpu_nic_firmware.rs
  • crates/api-core/src/tests/dpu_machine_update.rs
  • crates/api-core/src/tests/dpu_nic_firmware.rs
  • crates/api-core/src/tests/instance.rs
  • crates/api-core/src/tests/machine_update_manager.rs
  • crates/api-db/src/dpu_machine_update.rs
  • crates/api-model/src/dpu_machine_update.rs

Summary by CodeRabbit

  • Bug Fixes

    • DPF-managed machine updates are now correctly marked complete after reprovisioning, even when the resulting NIC firmware version is outside the configured allowlist.
    • Prevented completed DPF updates from being incorrectly reported as wrong-version failures.
    • Ensured update markers and related alerts are cleared when DPF reprovisioning finishes.
  • Tests

    • Added coverage validating successful completion handling for DPF-managed machines.

Walkthrough

The change adds DPF provenance to DpuMachineUpdate, propagates it from DPF-ingested hosts, and treats completed DPF updates as successful regardless of firmware allowlist membership. Tests verify marker cleanup, metric behavior, and explicit non-DPF initialization.

Changes

DPF firmware completion

Layer / File(s) Summary
Update provenance and discovery
crates/api-model/src/dpu_machine_update.rs
Adds dpf_managed to DpuMachineUpdate and sets it for DPF and non-DPF discovery paths.
Completed update propagation
crates/api-db/src/dpu_machine_update.rs
Derives DPF-management status from host ingestion configuration when constructing completed updates.
Completion handling and validation
crates/api-core/src/machine_update_manager/dpu_nic_firmware.rs, crates/api-core/src/tests/*
Routes DPF-managed completions through success handling, removes update markers, avoids wrong-version failure metrics, and updates test fixtures with explicit provenance values.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Sequence Diagram(s)

sequenceDiagram
  participant DPFDiscovery
  participant CompletedUpdates
  participant ClearCompletedUpdates
  participant UpdateHealth
  participant FirmwareMetrics
  DPFDiscovery->>CompletedUpdates: Set dpf_managed provenance
  CompletedUpdates->>ClearCompletedUpdates: Return completed DpuMachineUpdate
  ClearCompletedUpdates->>UpdateHealth: Remove update marker
  ClearCompletedUpdates->>FirmwareMetrics: Skip wrong-version failure metric
Loading
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the bug fix and identifies the affected DPF-host DPU firmware alert.
Description check ✅ Passed The description directly matches the code changes and tests, so it is clearly relevant to the changeset.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Comment @coderabbitai help to get the list of available commands.

@wminckler
wminckler merged commit 78d3881 into NVIDIA:main Jul 28, 2026
108 of 110 checks passed
@wminckler
wminckler deleted the fix/dpf-firmware-update-health-alert branch July 29, 2026 14:32
@wminckler
wminckler restored the fix/dpf-firmware-update-health-alert branch July 29, 2026 18:35
nv-dmendoza pushed a commit that referenced this pull request Jul 29, 2026
…4312)

Backport of #4236 to `release/v2.0` (upstream commit 7ba222e).

DPF-ingested hosts pick their DPU firmware update targets from the
DPUDeployment's expected BFB: `find_outdated_dpus` skips DPF hosts
outright, and `find_outdated_dpus_dpf` selects them by BFB hash instead.
The completion path, however, only removed the update markers when the
DPU's reported NIC firmware appeared in
`dpu_nic_firmware_update_versions` — a config list that only ever holds
NIC firmware strings. For a DPF host that comparison has no reason to
match, so a successful reprovision left the `HostUpdateInProgress` alert
pinned on the host forever.

That is not a cosmetic problem. The alert carries `prevent_allocations`,
so the host stayed unallocatable indefinitely, and its lingering alert
also made `is_available_for_updates` return false, excluding the host
from every later firmware update. Each manager pass additionally emitted
a bogus `WrongVersionAfterUpdate` outcome.

The fix carries the host's DPF-ingestion flag through `DpuMachineUpdate`
so the completion path can skip the NIC-version comparison for DPF
hosts. The rest of the completion gate is unchanged: the host must still
hold the update marker, be Ready, and have every DPU's reprovisioning
flag cleared. A DPF-driven reprovision finishing is itself the
completion signal.

## Related issues

None.

## Type of Change

- [ ] **Add** - New feature or capability
- [ ] **Change** - Changes in existing functionality
- [x] **Fix** - Bug fixes
- [ ] **Remove** - Removed features or deprecated functionality
- [ ] **Internal** - Internal changes (refactoring, tests, docs, etc.)

## Breaking Changes

- [ ] **This PR contains breaking changes**

## Testing

- [x] Unit tests added/updated

Adds `test_clear_completed_updates_dpf_host_off_list_version`, which
marks a host DPF-ingested, lands its DPU on a firmware version
deliberately outside the configured allowlist, and asserts the update
marker and its alert are both cleared. The test was confirmed
non-vacuous: neutralizing the `dpf_managed` branch makes it fail with
the exact production symptom (`Incorrect firmware version after
attempted update`, marker still pinned).

Full runs against a local Postgres, all green: `tests::dpu_nic_firmware`
(6), `tests::dpu_machine_update` and `tests::machine_update_manager`
(13),
`tests::instance::test_instance_creation_when_reprovision_is_triggered_parallel`,
and the complete `carbide-api-db` and `carbide-api-model` suites (575).

## Additional Notes

Two adaptations were needed relative to the upstream commit; the
production logic change itself is identical.

1. `crates/api-db/src/dpu_machine_update.rs` — upstream reads the flag
as `host_snapshot.config.dpf.used_for_ingestion`. On v2.0 `Machine` has
no `config` field, so this is `host_snapshot.dpf.used_for_ingestion`,
matching the existing usage in
`crates/api-model/src/dpu_machine_update.rs`.

2. `crates/api-core/src/tests/dpu_nic_firmware.rs` — the new test drops
two things absent from v2.0: the `reported_wrong_versions` field on
`DpuNicFirmwareUpdate`, and a `MetricsCapture`-based assertion that no
`wrong_version_after_update` failure is counted. v2.0 has no
wrong-version metric on this path at all. The health-report and alert
assertions, which are the actual regression coverage, are unchanged.

Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
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