Skip to content
61 changes: 58 additions & 3 deletions dev-tools/reconfigurator-cli/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use chrono::{DateTime, Utc};
use clap::{ArgAction, ValueEnum};
use clap::{Args, Parser, Subcommand};
use daft::Diffable;
use gateway_types::rot::RotSlot;
use iddqd::IdOrdMap;
use indent_write::fmt::IndentWriter;
use internal_dns_types::diff::DnsDiff;
Expand All @@ -22,7 +23,7 @@ use nexus_reconfigurator_planning::blueprint_builder::BlueprintBuilder;
use nexus_reconfigurator_planning::example::ExampleSystemBuilder;
use nexus_reconfigurator_planning::planner::Planner;
use nexus_reconfigurator_planning::system::{
SledBuilder, SledInventoryVisibility, SystemDescription,
RotStateOverrides, SledBuilder, SledInventoryVisibility, SystemDescription,
};
use nexus_reconfigurator_simulation::{BlueprintId, CollectionId, SimState};
use nexus_reconfigurator_simulation::{SimStateBuilder, SimTufRepoSource};
Expand Down Expand Up @@ -553,6 +554,27 @@ struct SledUpdateRotArgs {
/// sets the version reported for the RoT slot b
#[clap(long, required_unless_present_any = &["slot_a"])]
slot_b: Option<ExpectedVersion>,

/// sets whether we expect the "A" or "B" slot to be active
#[clap(long)]
active_slot: Option<RotSlot>,

/// sets the persistent boot preference written into the current
/// authoritative CFPA page (ping or pong).
#[clap(long)]
persistent_boot_preference: Option<RotSlot>,

/// sets the pending persistent boot preference written into the CFPA
/// scratch page that will become the persistent boot preference in the
/// authoritative CFPA page upon reboot, unless CFPA update of the
/// authoritative page fails for some reason
#[clap(long, num_args(0..=1))]
pending_persistent_boot_preference: Option<Option<RotSlot>>,

/// sets the transient boot preference, which overrides persistent
/// preference selection for a single boot (unimplemented)
#[clap(long, num_args(0..=1),)]
transient_boot_preference: Option<Option<RotSlot>>,
}

#[derive(Debug, Args)]
Expand Down Expand Up @@ -1706,6 +1728,31 @@ fn cmd_sled_update_rot(
if let Some(slot_b) = &args.slot_b {
labels.push(format!("slot b -> {}", slot_b));
}
if let Some(active_slot) = &args.active_slot {
labels.push(format!("active slot -> {}", active_slot));
}

if let Some(persistent_boot_preference) = &args.persistent_boot_preference {
labels.push(format!(
"persistent boot preference -> {}",
persistent_boot_preference
));
}

if let Some(pending_persistent_boot_preference) =
&args.pending_persistent_boot_preference
{
labels.push(format!(
"pending persistent boot preference -> {:?}",
pending_persistent_boot_preference
));
}
if let Some(transient_boot_preference) = &args.transient_boot_preference {
labels.push(format!(
"transient boot preference -> {:?}",
transient_boot_preference
));
}

assert!(
!labels.is_empty(),
Expand All @@ -1717,8 +1764,16 @@ fn cmd_sled_update_rot(
let sled_id = args.sled_id.to_sled_id(system.description())?;
system.description_mut().sled_update_rot_versions(
sled_id,
args.slot_a,
args.slot_b,
RotStateOverrides {
active_slot_override: args.active_slot,
slot_a_version_override: args.slot_a,
slot_b_version_override: args.slot_b,
persistent_boot_preference_override: args
.persistent_boot_preference,
pending_persistent_boot_preference_override: args
.pending_persistent_boot_preference,
transient_boot_preference_override: args.transient_boot_preference,
},
)?;

sim.commit_and_bump(
Expand Down
37 changes: 33 additions & 4 deletions dev-tools/reconfigurator-cli/tests/input/cmds-target-release.txt
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ blueprint-diff latest
# reflect that update has completed as well. Like before, collect inventory from
# it and use that collection for the next step. This should report that the
# update completed, remove that update, and add one for another sled.
sled-update-rot 98e6b7c2-2efa-41ca-b20a-0a4d61102fe6 --slot-a 1.0.0
sled-update-rot 98e6b7c2-2efa-41ca-b20a-0a4d61102fe6 --slot-b 1.0.0 --active-slot b --persistent-boot-preference b
inventory-generate
blueprint-plan latest latest
blueprint-diff latest
Expand Down Expand Up @@ -127,7 +127,7 @@ blueprint-diff latest

# Now simulate the update completing successfully.
# Like before, we should see a pending SP update for this sled.
sled-update-rot 2b8f0cb3-0295-4b3c-bc58-4fe88b57112c --slot-a 1.0.0
sled-update-rot 2b8f0cb3-0295-4b3c-bc58-4fe88b57112c --slot-b 1.0.0 --active-slot b --persistent-boot-preference b
inventory-generate
blueprint-plan latest latest
blueprint-diff latest
Expand Down Expand Up @@ -175,9 +175,38 @@ inventory-generate
blueprint-plan latest latest
blueprint-diff latest

# Update the RoT on the last sled.
# Now let's simulate an RoT update that hasn't completed by setting the persistent
# boot preference to a different slot than the active one. This should cause the
# planner to mark it as impossible, and replace it.
set ignore-impossible-mgs-updates-since now
sled-update-rot d81c6a84-79b8-4958-ae41-ea46c9b19763 --slot-b 1.0.0 --active-slot a --persistent-boot-preference b
inventory-generate
blueprint-plan latest latest
blueprint-diff latest

# An RoT update cannot continue if pending persistent boot preference is set.
# The slot B is set to a different version so it does not appear to be active
# and on the correct version, and the corresponding checks are triggered.
# Like before, this should cause the planner to mark it as impossible, and
# replace it.
set ignore-impossible-mgs-updates-since now
sled-update-rot d81c6a84-79b8-4958-ae41-ea46c9b19763 --slot-b 1.1.0 --active-slot b --persistent-boot-preference b --pending-persistent-boot-preference b
inventory-generate
blueprint-plan latest latest
blueprint-diff latest

# We do the same for transient boot preference. Note that we need to set the
# pending-persistent-boot-preference back to None
set ignore-impossible-mgs-updates-since now
sled-update-rot d81c6a84-79b8-4958-ae41-ea46c9b19763 --slot-b 1.1.0 --active-slot b --persistent-boot-preference b --transient-boot-preference b --pending-persistent-boot-preference
inventory-generate
blueprint-plan latest latest
blueprint-diff latest

# Update the RoT on the last sled. Note that we need to set the
# transient-boot-preference back to None
# There should be one last pending SP update.
sled-update-rot d81c6a84-79b8-4958-ae41-ea46c9b19763 --slot-a 1.0.0
sled-update-rot d81c6a84-79b8-4958-ae41-ea46c9b19763 --slot-b 1.0.0 --active-slot b --persistent-boot-preference b --transient-boot-preference
inventory-generate
blueprint-plan latest latest
blueprint-diff latest
Expand Down
8 changes: 8 additions & 0 deletions dev-tools/reconfigurator-cli/tests/input/cmds.txt
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,14 @@ sled-update-rot dde1c0e2-b10d-4621-b420-f179f7a7a00a --slot-a 4.0.0 --slot-b inv
sled-show dde1c0e2-b10d-4621-b420-f179f7a7a00a
sled-update-rot dde1c0e2-b10d-4621-b420-f179f7a7a00a --slot-a 4.0.0 --slot-b 5.0.0
sled-show dde1c0e2-b10d-4621-b420-f179f7a7a00a
sled-update-rot dde1c0e2-b10d-4621-b420-f179f7a7a00a --slot-b 6.0.0 --active-slot b
sled-show dde1c0e2-b10d-4621-b420-f179f7a7a00a
sled-update-rot dde1c0e2-b10d-4621-b420-f179f7a7a00a --slot-b 6.0.0 --active-slot b --persistent-boot-preference b
sled-show dde1c0e2-b10d-4621-b420-f179f7a7a00a
sled-update-rot dde1c0e2-b10d-4621-b420-f179f7a7a00a --slot-b 6.0.0 --active-slot a --persistent-boot-preference a --pending-persistent-boot-preference b --transient-boot-preference a
sled-show dde1c0e2-b10d-4621-b420-f179f7a7a00a
sled-update-rot dde1c0e2-b10d-4621-b420-f179f7a7a00a --slot-a 7.0.0 --pending-persistent-boot-preference --transient-boot-preference
sled-show dde1c0e2-b10d-4621-b420-f179f7a7a00a

sled-update-sp dde1c0e2-b10d-4621-b420-f179f7a7a00a
sled-update-sp dde1c0e2-b10d-4621-b420-f179f7a7a00a --active 1.0.0
Expand Down
Loading
Loading