There was no PDP-8/V made by Digital. So I am making one myself, Out Of Electron Valves.

The plan is there will be approx 320 tubes, specifically 6J6A. As of now, there is one board completed, the sequencer that contains the state flip-flops plus an instruction register latch (just the top four bits), and all the instruction decoding logic. That board uses 80 tubes, which is 160 gates. The tubes just do the inverting, the logic is done by crystal rectifiers. I just got it working (May 24, 2023) and it runs at 28k cps.

Each tube has 2 triodes. A single triode is required to make an AND-OR-INVERT gate. Three tubes (6 triodes) are required to make a D flipflop (ahem, edge-triggered, bi-stable multivibrator). Two tubes (4 triodes) are needed to make a latch.

The tubes are just the processor. For memory and I/O, I use a Raspberry PI. Transistors are used to do the level conversion between the RasPI and the tubes and to drive the LEDs. At some point, I might change the front panel to neons or incandescents with tube drivers, but LEDs will do for now.

When all the boards are done, it will run slower than 28k cps as there will be more circuitry for the bits to work their way through (27 levels of logic for the full processor as opposed to 10 for just the sequencer board). So that implies the processor will come in somewhere around 10k cps, though I wouldn't be surprised at 5k cps cuz of longer circuit traces.

There are going to be a total of five tubulated boards, the sequencer (completed), the MA register (on order), the PC register, the AC/Link register, and the ALU. There are also the backplane board and transistorized front panel board as shown below.

Here is a video of it running slowly (~5 cps) to see the lights blinking. The laptop is showing the RasPI output displaying the states. The FETCH-DEFER-EXEC-INTAK LEDs are stepping through the various states as the RasPI clocks the processor and sends it random opcodes. The top three bits of the instruction are shown in the IR LEDs. The RasPI checks the GPIO pins at the end of each cycle to make sure they are what they should be, as the RasPI knows what state the processor should be in for every cycle.

sequencer board - 80 tubes - the crystal rectifiers are on the back
sequencer board crystal rectifiers (and fan pointed at the tubes!)
front panel - the whole thing is tipped on its side. RasPI is in bottom center of pic mounted to front panel board.
8-tube board - the 80 tubes on the sequencer board are really 10 of these boards, all identical, each containing 16 generic inverters. They plug into the back of the large crystal rectifier board which gives them their individual personality. 32 more of these boards will have to be constructed, and plugged into the crystal rectifier boards, to complete the PDP-8/V.
 
Each 8-tube board requires +120V@45mA, -96V@35mA, +5V@10mA, 48V@400mA (8 6V filaments wired in series).
 
The allocation of the 8-tube boards to the crystal rectifier boards are:
  • ACL (accum/link) - 8 x 8-tube boards
  • ALU (arith/logic) - 10 x 8-tube boards
  • MA (mem address) - 6 x 8-tube boards
  • PC (prog counter) - 8 x 8-tube boards
  • SEQ (state machine) - 10 x 8-tube boards
the SEQ board with one of the 8-tube boards removed

When all said and done, I estimate it will use about a kilowatt of power total, about the same amount as a small space heater.

Here is another video, this one shows the processor running at 28k cps. Again, the RasPI verifies the GPIO pins at the end of each cycle to make sure it is working correctly. If I speed it up to 30k cps, the RasPI is quick to catch the errors.

Early on, there were the:

You may also be interested in the Hode retro-computing project.

8-tube board section
Making an and-or-invert gate with crystal rectifiers and an 8-tube board section
D-flipflop from 6 NAND gates (diagram from Wikipedia)
  • whenever Clock is low, B and C are high regardless of Data input, leaving E/F SR-FF output steady
  • Data being low for setup time lets it soak into A making A high, then that soaks into D making D low (cuz C is being held high by the low Clock)
  • then when Clock goes high, A is high, D is low, B goes low, driving E high and F low
  • D stays low, C stays high
  • if Data goes high (after being low for hold time after Clock) with Clock still high, B is still low, so A stays high, so nothing changes
  • Data being high for setup time lets it soak into A making A low (cuz B is held high by the low clock), then that soaks into D making D high
  • then when Clock goes high, B stays high (cuz A is low), C goes low (cuz D is high), driving F high and E low
  • if Data goes low (after being high for hold time after Clock) with Clock still high, A goes high, B and D stay high cuz C is still low, so nothing changes
  • Setup time would be however long it takes for the A B C D gates to stabilize after a Data change with Clock staying low. So Data has to soak (1) all the way through A, (2) into B's input and all the way through D, (3) into C's input.
  • Hold time would be however long it takes for the A B C D gates to block changes in Data after Clock goes high. So Clock has to soak (1) all the way through B or C, (2) B soaks into A's input or C soaks into B's and D's input.

STATES

FETCH1 RasPI.Data,ALU = PC
RasPI.MemRead = 1
FETCH2
FETCH2 IR ← RasPI.Data
MA ← ALU = PC,RasPI.Data
PC ← PC + 1
DEFER1 or EXEC1
DEFER1 RasPI.Data,ALU = MA
RasPI.MemRead = 1
RasPI.MemWrite = auto-increment ? 1 : 0
DEFER2
DEFER2 MA ← RasPI.Data EXEC1 or DEFER3
DEFER3 MA ← RasPI.Data,ALU = MA plus 1 EXEC1
EXEC1/AND RasPI.Data,ALU = MA
RasPI.MemRead = 1
EXEC2/AND
EXEC2/AND AC ← ALU = AC and RasPI.Data FETCH1 or INTAK1
EXEC1/TAD RasPI.Data,ALU = MA
RasPI.MemRead = 1
EXEC2/TAD
EXEC2/TAD MA ← ALU = RasPI.Data EXEC3/TAD
EXEC3/TAD L,AC ← ALU = L,AC plus MA FETCH1 or INTAK1
EXEC1/ISZ RasPI.Data,ALU = MA
RasPI.MemRead = 1
RasPI.MemWrite = 1
EXEC2/ISZ
EXEC2/ISZ MA ← ALU = RasPI.Data EXEC3/ISZ
EXEC3/ISZ RasPI.Data,ALU = MA plus 1
PC ← PC + carry
FETCH1 or INTAK1
EXEC1/DCA RasPI.Data,ALU = MA
RasPi.MemWrite = 1
EXEC2/DCA
EXEC2/DCA RasPI.Data,ALU = AC
AC ← 0
FETCH1 or INTAK1
EXEC1/JMS RasPI.Data,ALU = MA
RasPI.MemWrite = 1
EXEC1/JMS
EXEC2/JMS RasPI.Data,ALU = PC EXEC2/JMS
EXEC3/JMS PC ← RasPI.Data,ALU = MA plus 1
RasPI.MemRead = interrupt request ? 0 : 1
FETCH2 or INTAK1
EXEC1/JMP PC ← RasPI.Data,ALU = MA
RasPI.MemRead = interrupt request ? 0 : 1
FETCH2 or INTAK1
EXEC1/IOT RasPI.Data,ALU = AC
RasPI.Link = L
RasPI.DoIO = 1
EXEC2/IOT
EXEC2/IOT AC ← ALU = RasPI.Data
L ← RasPI.Link
PC ← PC + RasPI.IOSkip
FETCH1 or INTAK1
EXEC1/Group1 AC ← ALU = AC modified by instruction FETCH1 or INTAK1
EXEC1/Group2 PC ← RasPI.Data,ALU = PC + skip ? 1 : 0
RasPI.MemRead = interrupt request ? 0 : 1
if CLA, AC ← 0
FETCH2 or INTAK1
INTAK1 RasPI.IntAck = 1
MA ← RasPI.Data,ALU = 0
RasPI.MemWrite = 1
IR ← JMS 0
EXEC2/JMS

Update as of May 28, 2023

front panel standing up
video standing up
+120V power supply with 80 tubes plugged in
other power supplies with 80 tubes plugged in
the filament power supply is on the left with the big capacitor on a piggy-back circuit board to soft-start the filaments