Engineering Notes
What the Origin 300 Firmware Insisted On
Getting a two-processor Origin 300 to boot its stock diagnostics reliably meant describing the machine's processors, network identity and reset state the way the firmware checks them, and then surviving the emulator's own SMP timing.
The Origin 300 is SGI’s machine after the Origin 200, a server built on the Bedrock node controller instead of the Hub, and the first of the generation this project calls SN1. Its model is on the fork trunk and register-tested down to its address map and PCI routing. But a register test drives a device with no operating system running, and none of it gets the machine’s own firmware to say a word.
Getting the stock IP35 PROM from that silence to its ALL DIAGS PASSED line took two kinds of work.
First, describing the machine the way the firmware insists on: three of the fixes below were the same
shape, the firmware exacting about what the machine tells it about itself, and each time our model had
told it something slightly wrong. Then, once it would boot at all, making two processors boot together
survive the emulator’s own timing.
These were the walls before the operating system. IRIX itself has since installed and booted to a login on the machine, which its own announcement covers. And a firmware that runs on our machine is evidence about our machine, never about the silicon.
Two empty sockets it would not overlook
The Origin 300 this project models carries two processors, and the PROM that boots it, version 6.210, is written for a board that can hold four. It checks all four positions at power-on. Our machine fits two and leaves the other two empty, and the firmware read those empty positions not as absent but as processors that had failed to start. It printed processor clock-retry lines and would not settle.
The fix is not to invent two more processors. It is to tell the firmware, in the one place it reads,
that the empty positions are disabled on purpose. The PROM keeps a small writable environment in its
boot flash, and two of its variables name exactly those positions. A machine that seeds them before
the firmware runs describes an intended two-processor population rather than a four-processor one with
two failures. With them seeded, PROM 6.210 powers up once, prints no retry line, enables two
processors and no disabled ones, and reaches ALL DIAGS PASSED and its maintenance menu. A second
boot from the resulting flash does the same. The model seeds those records only for a fresh machine,
and leaves a supplied or reused flash image untouched.
An Ethernet address one byte out of place
The next wall was on the network. The firmware reads its own Ethernet address out of a board-identity record, an ASCII field in the base-I/O board’s area. Our generated record placed that field one byte past where the published layout puts it. The firmware read the byte before the real address, with the rest of the string shifted along, found characters that were not the hex digits it expected, and treated the whole thing as a bad address. A netboot could still be forced by handing the address to the firmware on its command line, but left to read the board for itself the firmware had nothing usable.
The fix encodes the board record to its published boundaries, an 80-byte board area and a 16-byte
chassis area, with each identity field at its stated offset, and takes the I/O controller’s Ethernet
address from that same record. With the field where the firmware looks, the stock PROM reads its
address and boot -f bootp()/sash64 reaches the standalone sash: shell over the network with no
command-line override. That shell is the program that installs and boots IRIX. Reaching it is not an
IRIX kernel boot, and whether a real machine fits the one-wire identity part this address would
otherwise come from is still an open question.
The Config0 value the firmware settled for us
The last of the three is the one where the firmware answered a question the project could not. The
R14000 processor’s Config0 register has a reset value, and the project’s datasheet carried two
candidates for it that differ in a handful of bits, one field reading four in the first and three in
the second, 0xa985 against 0xa785 in the low half. The datasheet had the discrepancy marked
unresolved, with a note that only a trace of the firmware handling the register would settle it.
The firmware settled it. Followed deterministically through its cold-reset election, the PROM loads a
header word, 0x5219a785, out of its local flash view, and checks the processor’s Config0 against
it, the low sixteen bits and one byte above them. The value carried in the processor’s updater
payload, the one reading four, fails that check. The other candidate, 0x0019a785, passes, and the
firmware goes on to boot. The machine did not need the datasheet to choose. The firmware named the
value it would accept by rejecting the other, and the datasheet now records 0x0019a785 as the reset
value on the firmware’s own evidence rather than the updater’s.
And then it had to survive being a multiprocessor
Describing the machine right got one processor through the diagnostics. Two was a different problem, and not a firmware one: it was the emulator’s own timing.
The Origin 300 boots its two processors through a rendezvous. Each writes a flag to a shared node-controller scratch register and then polls it until the other has arrived. Under the multi-threaded translator, where each processor runs on its own host thread, the two can reach that point badly out of step. A processor that arrives late still does its own reset housekeeping, and one of those writes lands on the very scratch register the rendezvous uses, after the boot master has already posted its flag there, and erases it. The master polls a register that has gone back to zero, times out, and carries on as though that processor were never there. The two-CPU boot would then come up reporting one processor, or fall over before the menu. The fix holds a processor’s later write to that register until every other running processor has made its own first write since reset, which restores the same-instant join that real hardware gets for free from a shared reset line. It is the Bedrock cousin of the hold that recovered a lost processor pair on the Origin 2000, one node controller’s mailbox later.
The other was in the USB host controller. The base-I/O board’s firmware brings the controller up, then reads its frame counter about a millisecond later and expects it to have moved. The model only advanced that counter from a timer callback the main loop runs a little after each frame boundary, so under host scheduling pressure the read could land while the counter still read zero, and the firmware’s handling of a zero there followed a null pointer and crashed the boot. The fix runs any overdue frame boundary at the moment of the read, so the counter tracks the clock rather than a callback that has not fired yet. With both in place, the two-processor boot reaches the maintenance menu reliably on the trunk rather than once in a while on a branch.
What it bought
The two-processor Origin 300 boots its stock firmware to the maintenance menu, both processors enabled and its diagnostics passing, reliably and on the project’s main line. From that menu the machine went on to netboot SGI’s standalone shell and then to install and boot IRIX. What the firmware measured along the way is worth having: the stock firmware of a machine nothing had emulated before now runs far enough to check its own hardware and stop when the hardware is wrong, and every time it stopped, the complaint was right.