Who may reach this board, from the interface that asks for the password
Pins bmcd 2.36.0 and BMC-UI 3.27.0; tpi is unchanged and already current.

Firmware v2.28.0, 12 September 2026 — the first image to carry bmcd 2.36.0, BMC-UI 3.27.0. Every item below is the repository's own changelog entry, taken apart; the whole entry is a click away under each one.
New¶
Who may reach a board, from the interface that asks for the password¶
Settings gains a card for the two things that decide who gets in and which until now existed only on the filesystem: the local password, and the certificate authority whose client certificates may name an operator.
The whole entry
It shows how you got here first, because an operator arriving through the fleet is not holding the board's password and the rest of the card reads differently depending on which you are.
The daemon's rules appear as disabled controls rather than refusals after the fact: the current password is required even from an operator a proxy vouched for, twelve characters counted as characters, and "stop trusting any proxy" is unavailable when you are authenticated by that proxy.
Who may reach this board, from the interface that asks for the password¶
bmcd 2.36.0
(SQU-209). Both halves of this board's access control used to live only on its filesystem and arrive over SSH: the local password through passwd on a console, the client CA through a script in another repository.
The whole entry
Nothing in the web interface could answer "who can get in", and the one interface that demands a password every time could not change it.
GET /api/bmc/access now answers with the local account, the trust anchor
for proxied identity if one is in effect — subject, issuer, expiry and a
SHA-256 fingerprint to compare against the proxy's — the header an identity
is read from and which of config/override/default chose it, and how the
asking request was itself authenticated. A page can now say "you are here
as [email protected], vouched for by the gateway" rather than guess.
POST /api/bmc/access/password changes a local password, and
PUT/DELETE /api/bmc/access/client-ca set and remove the trust anchor.
Not through the legacy dispatcher, and that is the point. Every
opt=set call is written to the audit log with its whole query string, so a
password routed that way would be recorded in clear in bmcd.<date>.log and
in remote syslog when SQU-108 lands. These take a JSON body and log the
action and the actor, never the secret.
The rules each exist because of a specific way this could go wrong:
- The current password is required, including from an operator a proxy vouched for. A certificate proves the gateway trusts you; it does not prove you hold this board's console, and a change made without the old password is a lockout anyone with a live session can perform.
- Twelve characters, counted as characters. A passphrase is not shorter
because it is written in Cyrillic, and
BanPatrolslows an online guess but does nothing for a stolen/etc/shadow. - A wrong password and an account that does not exist get the same refusal, so this cannot be used to enumerate accounts.
chpasswd, with the pair on stdin. Not a shell and not a command line: this daemon runs as root, and a password inargvis inpsfor anyone on the box.- A CA bundle is loaded the way the TLS acceptor will load it, before it
is stored. A bundle that cannot be loaded makes the daemon fail to
start — which is exactly why
client_cawas never safe to ship in a defaultconfig.yaml— so it must never reach the disk. - Removing the CA is refused when the caller is authenticated by it. That request ends its own session, through the proxy it is asking through. Do it from the board's own interface, with a password.
The daemon does not rewrite config.yaml. That file is the operator's,
it carries comments, and the daemon reads it with a crate that has no
writer. So the interface owns two small files instead — the bundle itself at
a fixed path, and a JSON sidecar for the header name — and config.yaml
still wins wherever it speaks. Where it pinned a value, these endpoints
refuse to touch it and say so.
A consequence worth having: client_ca now falls back to that fixed path
when the file exists, so a board whose anchor was removed comes back up
instead of refusing to start.
The firmware listing survives a reboot¶
bmcd 2.35.0
At /mnt/overlay/firmware-catalog.json.
The whole entry
Asking four sources takes between 75 and 230 seconds and spends GitHub's unauthenticated quota of sixty an hour four at a time, and all of it used to be thrown away by every reboot — so the first person to open the Firmware page after an upgrade, the person most likely to be looking, paid for the lot.
It sits beside firmware-sources.json and on the overlay for the same
reason: both firmware images mount it, so it survives an A/B promotion. The
board answers from it at once and refreshes behind that answer. The age it
reports comes from the timestamp inside the file rather than the file's
mtime, because what a reader needs is when the sources were asked, and an
age that parses to something absurd is clamped to a day.
It is written only when the offering changes. The overlay is NAND and UBI reports five free eraseblocks of 2040 on the reference board; a listing rewritten every half hour would be thousands of writes a year for bytes that change when somebody publishes a release. The comparison is on what the sources offer, not the whole record, because the timestamp moves every time.
Only a complete answer is stored: a fan-out where one source errored is good enough to show, because the page renders the error, and not good enough to become the listing a board boots with.
Settings can say who may get in¶
BMC-UI 3.27.0
The access card: how you arrived, the password for the local account, and the certificate authority a proxy must hold to name you — the first time either half was visible from the interface, let alone changeable there.
Fixed¶
-
The fleet's serial console could not connect. It refused before opening a socket, demanding a session token the fleet has no reason to hold, while every other tab on the same page answered normally.
The whole entry
The certificate was never involved: the browser talks to its own origin and never to a board. Through the gateway the browser presents nothing, and the identity is attached on a hop it is not part of.
Proved against bmc-1 through a stand-in for the gateway —
101 Switching Protocols, subprotocolbmcd.serial.v1— and then "connected" in a real browser with zero console errors.
Note¶
v2.26.0 and v2.27.0 were released without entries here. What they carried is recorded in the package hash files, which document every pin bump with its measurement: BMC-UI 3.25.0 (the SD card picker and two dead flash buttons) and 3.26.0 (temperature on Board Health, an honest console hint), and bmcd 2.35.0 (the catalogue refresh that could wedge for ever, and the on-disk listing).
-
The board could stop checking for firmware, for ever. (SQU-201). The Firmware page said checking the sources now and never stopped, with Check now disabled beside it, and no later refresh could start. Only restarting the daemon cleared it. bmcd 2.35.0
The whole entry
Opening the Firmware tab on a board whose cached listing had aged out was enough to trigger it; bmc-2 sat that way for three and a half hours on 2026-09-11 with
refreshing: true, the timestamp frozen, and no fan-out process running at all.The claim that says "a refresh is running" was an
AtomicBool, taken before the work and released by aDropguard. That is correct for a panic and wrong for everything else: a task dropped before its first poll constructs no guard, and a blocking join that never returns never drops one.It is a deadline now, and a deadline cannot be lost — the claim expires whether or not anything is left to release it. Three things release it and it takes all three: the guard for a panic, a
tokio::time::timeoutaround the fan-out for a blocking join that never returns, and the deadline for the case where neither of the other two exists. The dedup that stops "check now" turning four sources into twelve requests is kept as a compare-exchange.The bound is ten minutes. Not a guess at the work: the fan-out was 74–78 s when first measured, and on 2026-09-12 took 75–100 s on bmc-1 and about 230 s on bmc-2. It is how long a lost refresh may block every future one.
-
The fleet's serial console connects. It was one gate away: the certificate path was already wired end to end, and the interface refused before trying. BMC-UI 3.27.0
Every release of the firmware · the roadmap · follow by feed