Atomized

The Secret 9100

I’ve been doing some digging into the Fluke 9100 software and have found a few interesting things. I was hoping to figure out a bit more about this stuff, but haven’t had the time to devote to it and figured I’d share what I know in the hopes that someone else wants to pick it up.

The 9100 series is a family of test/troubleshooting systems manufactured by Fluke from the late 1980s through the mid 1990s. They’re m68k-based machines which run the OS-9 RTOS, with specialized hardware for interfacing with the system being tested.

OS-9 Programmer Credits

This easter egg was left by the programmers of OS-9. The 9100 System software from V4.2 - V5.0 contains this string:

>>>>>>>>>>>>>>>>from the disk of Robert Doggett <<<<<<<<<<<<<<<<

While V6.0-V6.1 has:

<<<<<<<**>>>>>>>From the disk of Robert Doggett Larry Crane  and Warren Brown <<<<<<<**>>>>>>>

Earlier versions don’t contain the easter egg.

Robert Doggett was one of the earliest OS-9 programmers, going back to the 6809 / CoCo days in the early 1980s.

I don’t know if there’s a way to trigger this, or if the strings were just left in the binaries for people to find. I suspect there’s no way for a 9100 display this message.

9100 Team Credits

There is also an easter egg left by the team at Fluke who built the system. It definitely is supposed to be run from TL/1. I know the command, and I know what it should do, but I haven’t been able to make it work. I think it needs a specific argument which I haven’t been able to find yet.

The command is ' credits ', exactly like that, with a spaces on either side and single quoted. The ability to have function names with spaces in them, and to refer to them by single quoting is an undocumented TL/1 feature. I don’t know if you can define your own programs/functions like this, but there are at least two built-in ones that do it.

When you call it, it will print the names of the team at Fluke who built the 9100:

Software Engineers
Credit

David Bezold
Project Management

Meg Lloyd
Editor, Tests

David (Doctor) Jacobson
Tests

Patsy Thiemens
Control

Mariano Landicho
User Interface

Janet Terry
GFI

Kurt Guntheroth
TL/1

James (The Destroyer) Peckol
Errors and Faults

Gregg Strand
Probe & I/O Module

Jeff (Moriarty) Meyer
Operating System

Tom Anderson
Floating Point and Mods

Bruce Twito
Court Jester

Christopher Hoskin, Unindicted Co-conspirator

I’m not sure if this prints on the operator’s display with a delay, or dumps out to the video display. I lean towards the VFD, since the text seems to be sized close to what it can display.

Development Strings

There are some strings left over from development of the 9100. rtsctl is the interpreter for TL/1, the 9100’s built in programming language, and it has this random string:

/HDR/TMP/KURT

There are also some version control artifacts from the source code in rtsctl. They were using RCS, and put $Header$ keywords in their source. When you check a file in to source control, RCS replaces this with some metadata, like timestamp, author, version, etc. RCS is the ancestor to CVS, and was very commonly used in the 1980s.

These are examples pulled from every version of the software I have available.

You can see several logins here which correspond to names in the credits.

fault_handling.c

$Header: /medusa/usr2/kgpt/quest/src/TRM/primitives/RCS/fault_handling.c,v 1.21 87/12/14 15:50:14 gregg Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/fault_handling.c,v 1.23 88/10/21 11:03:12 brucet Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/fault_handling.c,v 1.24 90/01/24 15:28:26 brucet Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/fault_handling.c,v 1.27 91/01/17 10:53:12 fleming Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/fault_handling.c,v 1.27 91/01/17 10:53:12 fleming Exp $

globals.c

$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/globals.c,v 1.7 87/03/20 15:46:53 jacobson Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/globals.c,v 1.7 87/03/20 15:46:53 jacobson Exp $
$Header: /medusa/usr2/kgpt/quest/src/TRM/primitives/RCS/globals.c,v 1.7 87/03/20 15:46:53 jacobson Exp $

primFaults.c

$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/primFaults.c,v 1.13 87/08/14 09:39:53 brucet Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/primFaults.c,v 1.13 87/08/14 09:39:53 brucet Exp $
$Header: /medusa/usr2/kgpt/quest/src/TRM/primitives/RCS/primFaults.c,v 1.13 87/08/14 09:39:53 brucet Exp $

primitives.c

$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/primitives.c,v 1.39 88/02/26 12:59:02 brucet Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/primitives.c,v 1.41 88/09/13 11:44:20 brucet Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/primitives.c,v 1.42 89/09/05 15:14:31 gregg Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/primitives.c,v 1.43 90/02/05 14:41:12 brucet Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/primitives.c,v 1.43 90/02/05 14:41:12 brucet Exp $

sctimer.c

$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/sctimer.c,v 1.10 87/03/20 15:49:33 jacobson Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/sctimer.c,v 1.10 87/03/20 15:49:33 jacobson Exp $
$Header: /medusa/usr2/kgpt/quest/src/TRM/primitives/RCS/sctimer.c,v 1.10 87/03/20 15:49:33 jacobson Exp $

spaces.c

$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/spaces.c,v 1.5 86/12/01 12:43:19 jacobson Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/spaces.c,v 1.5 86/12/01 12:43:19 jacobson Exp $
$Header: /medusa/usr2/kgpt/quest/src/TRM/primitives/RCS/spaces.c,v 1.5 86/12/01 12:43:19 jacobson Exp $

support.c

$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/support.c,v 1.9 87/12/04 15:48:12 bezold Exp $
$Header: /daphne/usr2/kgpt/quest/src/TRM/primitives/RCS/support.c,v 1.9 87/12/04 15:48:12 bezold Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/support.c,v 1.9 87/12/04 15:48:12 bezold Exp $
$Header: /daphne/usr2/quest/src/TRM/primitives/RCS/support.c,v 1.9 87/12/04 15:48:12 bezold Exp $
$Header: /medusa/usr2/kgpt/quest/src/TRM/primitives/RCS/support.c,v 1.9 87/12/04 15:48:12 bezold Exp $

It looks like they either had two development machines, or one machine with two disks, and an ancient Greek theme.

Softkey Profiles

When using EDITOR, the softkeys shown on the video display change based on the type of file you have open. These are defined by the contents of /SYSDISK/PROFILES/FOO, with FOO being the type of file currently open. Each profile is a plain text file. This is the conents of PROGRAM:

0 gotoline gotoline 1 GOTO
1 save save 3 SAVE
2 qdebug qdebug 1 DEBUG
3 mark mark 9 MARK
4 cut cutb 8 CUT
5 yank yankb 8 YANK
6 pastea pasteb 1 PASTE
7 replacef replaceb 1 REPL
8 searchf searchb 5 SEARCH
9 check togcheck 1 CHECK
-
*

The format is:

INDEX NORMAL-COMAND SHIFT-COMMAND ??? LABEL

The index corresponds to the softkey, 0 = F1, 1 = F2 and so on.

The next field is the name of an internal EDITOR command to invoke when you press the softkey. I believe this is the complete list of valid commands:

  • beep — Make the mainframe beep. This is used when there’s no action assigned to the softkey.
  • cadtrans — Launch CAD translator.
  • check — Check syntax of the current TL/1 program.
  • colsel — Select column. Used in response files.
  • compile — Compile programs. Used in UUT views with shift-F3. Different from scompile somehow?
  • cover_nf — Alternate coverage function, not sure what it does.
  • coverage — Generate GFI coverage summary for a UUT.
  • cutb — Cut (backwards?).
  • delete — Delete an entry from a response file.
  • edvterm — Terminal emulator.
  • eqfault — Unknown.
  • eqsedit — Unknown.
  • eqsquit — Unknown.
  • format — Format a disk.
  • gotoline — Goes to a specific line of many different file types.
  • insert — Insert a response.
  • learn — Learn a response.
  • mark — Mark text.
  • offset — Change response offset.
  • other — Unknown.
  • pastea — Paste from buffer #1 into file.
  • pasteb — Paste from buffer #2 into file.
  • qcopy — Copy a file.
  • qdebug — Enter the TL/1 debugger.
  • quit! — Unknown. Quit to operator’s panel?
  • remove — Delete a file.
  • renum — Unknown. Renumer?
  • replaceb — Replace text backwards.
  • replacef — Replace text forwards.
  • save — Save file.
  • scompile — Compile file, in UUT view. Normal version.
  • searchb — Search backwards in file.
  • searchf — Search forwards in file.
  • select — Select a response in a response file.
  • style — Change color scheme.
  • swapscr — Show more softkeys in response files.
  • tlcomp — Compile program (in proglib) or pod file.
  • tlscomp — Compile program (in proglib) or pod file. Silent??
  • togcheck — Shift-F10 command in node and program files. Toggles whether line-by-line syntax checking is enabled, e.g. prevents you from moving off a line with a syntax error.
  • yank — Put marked text into buffer #1.
  • yankb — Put marked text into buffer #2.

I haven’t actually tried changing any of these, but I’m certain this is how they work.

I’ve got no idea what the second-to-last number is.

Executing System Functions

The most interesting thing I found is an undocumented TL/1 command. I found this while I was trying to figure out what "9100A Install Disk V3.0" was. I’m still not completely sure what this disk is for. It looks like perhaps it was an internal tool used at Fluke to verify that the OS was loaded onto 9100As on the production line. And/or the V2.0->V3.0 required some backwards-incompatible changes, and this was to deal with those. Possibly both.

The disk is full of interesting things. It has a several compiled OS-9 programs, and two TL/1 programs. The TL/1 programs use an undocumented function to call the OS-9 binaries. This function takes the format:

'execute system function' name "/path/to/program", arg1 "arg", arg2 "arg", ...

You can specify up to 5 arguments.

This is awesome, because it means if someone locates a copy of the OS-9/68000 compiler and toolchain, programs can be written in C and called from TL/1, which could significantly bridge gaps in TL/1’s functionality. In particular, moving files around via the serial port is painful, because it requires a lot of manual input for each file. This could open the door to improving that significantly.

"Jane"

There are some references to "jane" in multiple places in the 9100 documentation and programs. Every version of the system software I’ve seen has a file named /HDR/ROM/janeconfig. It seems to be an OS-9 binary, and it has some strings in it explaining how to invoke it:

Usage: %s podname filepath
Pod Name = %s
File Path = %s

... but not what it does. It’s present all the way back to the V3.0 software, the oldest I have a copy of.

Later versions removed the podname argument:

Usage: %s filepath
File Path = %s

Another reference is in the 9100FT schematics:

/assets/blog/2018/10/14/the-secret-9100/jane-sync-access.png

Figure 1: 34-pin JANE SYNC ACCESS connector

This is a test connector, which you’d plug a 9132FT’s sync pod into, if you needed to test or troubleshoot a 9100FT with another 9100FT. The 9100A doesn’t have this connector, but the references to "janeconfig" most definitely predate the FT. The 9132 pods require some setup, maybe this program is what saves and loads it.

Still, "jane" is a fairly unusual name. Maybe it was an internal code name for the 9132.