SnmpKit.SnmpSim.Device.ModemUpgrade (snmpkit v0.6.6)

State machine and helpers for DOCSIS modem firmware upgrade simulation.

Supported core OIDs (per feature request):

  • docsIfDocsDevSwAdminStatus — 1.3.6.1.2.1.69.1.3.1.0 (INTEGER; read-write)
  • docsIfDocsDevSwOperStatus — 1.3.6.1.2.1.69.1.3.2.0 (INTEGER; read-only)
  • docsIfDocsDevSwServer — 1.3.6.1.2.1.69.1.3.3.0 (OCTET STRING; read-write)
  • docsIfDocsDevSwFilename — 1.3.6.1.2.1.69.1.3.4.0 (OCTET STRING; read-write)

Notes:

  • AdminStatus write triggers the upgrade when set to a specific value (we use 3 for "upgradeFromMgt" by default).
  • OperStatus transitions through realistic steps with configurable timings.
  • Errors map to SNMP statuses at the PDU processor layer; here we return pure state and let callers map to errors.

Summary

Functions

Advance the upgrade to the next phase. Returns {scheduled_msgs, new_state}.

Apply a simple field SET for server/filename/admin. Returns updated state. Validation is basic here; callers should enforce SNMP type checks.

Build default upgrade state. Accepts optional opts

Trigger the upgrade. Returns {scheduled_msgs, new_state}.

Types

t()

@type t() :: %{
  server: String.t(),
  filename: String.t(),
  admin_status: integer(),
  oper_status: integer(),
  progress: integer(),
  started_at_ms: integer() | nil,
  upgrade_enabled: boolean(),
  post_upgrade_version: String.t() | nil,
  default_version: String.t() | nil,
  invalid_server_regex: Regex.t() | nil,
  delay_ms: %{
    name_check: non_neg_integer(),
    download: non_neg_integer(),
    apply: non_neg_integer()
  }
}

Functions

advance_phase(state, atom)

@spec advance_phase(t(), :checking_name | :download | :apply) :: {list(), t()}

Advance the upgrade to the next phase. Returns {scheduled_msgs, new_state}.

apply_set(field, value, state)

@spec apply_set(:server | :filename | :admin_status, term(), t()) :: t()

Apply a simple field SET for server/filename/admin. Returns updated state. Validation is basic here; callers should enforce SNMP type checks.

default_state(opts \\ %{})

@spec default_state(map()) :: t()

Build default upgrade state. Accepts optional opts:

  • upgrade_enabled: boolean (default true)
  • upgrade_delay_ms: %{name_check:, download:, apply:}
  • invalid_server_regex: Regex
  • default_version: string
  • post_upgrade_version: string

trigger(state, opts \\ [])

@spec trigger(
  t(),
  keyword()
) :: {list(), t()}

Trigger the upgrade. Returns {scheduled_msgs, new_state}.

For test simplicity, we complete immediately without timers. If preconditions are not met (server/filename invalid or upgrade disabled), we return unchanged state (or failed state when invalid_server_regex matches).