|
GE-115 Emulator
An Emulator of the General Electrics GE-115 computer
|
The CPU micro-sequences are documented as the flow-chart foldout set drawing 14023130 (and the parallel timing charts 14024137) in CPU/GE 120 CENTRAL PROCESSOR [7].pdf — Volume 7, the schematics binder (its index, render-page 2, lists item 2 = Flow charts 14023130, item 3 = Timing charts 14024137). Each foldout is one "sequence" sheet; the boxes are CPU states (top-left label = the SO/SA state code in hex, e.g. 64 65, C8, 80), the right column is the command code(s) issued (COxx/CIxx/CExx/CUxx), and the bracketed text is the firing condition. gemu's msl-states.c charts are a direct transcription of these (struct msl_timing_chart = {clock, command, condition, additional}).
This file maps each flow-chart sheet to the gemu state(s) that implement it and records the verification status. It was built by rendering CPU[7] with pdftoppm (the OCR text layer does not contain the foldouts) and reading the title blocks + box labels. Render-page numbers are 1-based pages of CPU[7].
| CPU[7] render‑pg | Drawing | Sheet title | gemu state(s) | Status |
|---|---|---|---|---|
| 23 | 14023130 | FASE ALFA / ALPHA PHASE | e2/e3, e0, e4, e6, e5, e7 (+ ec/ed, ee/ef indexing) | ✅ faithful (alpha + modified-index micro-cycle) |
| 24 | 14023130A | DISPLAY SEQUENCE | 00 | ✅ verified row-by-row |
| 25 | 14023130B | FORCING SEQUENCE | 08 | ◑ states match; a few bracket conditions need a higher-DPI/physical recheck |
| 26 | 14023130C | INTERRUPTION | F0,D2,D3,D0,D1 | ✅ implemented (PSR save → 0x0300) + test |
| 27 | 14023130D | LPSR SEQUENCE | C2,C3,C0,C1 | ✅ implemented as the interrupt restore (load new PSR ← 0x0304); the 0x9d LPSR instruction entry still TODO |
| 28 | 14023130… | JS1/JS2/JIE/JC/NOP2/HLT/INS/ENS/LON/LOFF/LOLL SEQUENCES | 64/65 (jc_js1_js2_jie, nop, lon_loll, ins, ens, loff, HLT) | ◑ hybrid (functionally wired, not per-clock) |
| 29 | 14023130E | JU‑JC‑JRT‑JS‑JE SEQUENCE | 64/65 jump path (CI00s, verified_condition, JRT_LINK) | ◑ hybrid (validated by tests/exec.c jumps + JRT) |
| 30 | 14023130… | LR‑AMR‑CMR‑SMR‑STR SEQUENCES | 64/65 (EXEC_LR/STR/CMR/AMR/SMR) | ◑ hybrid (validated by tests/exec.c reg ops) |
| 31 | 14023130O | NI‑XI‑OI‑TM SEQUENCES | 64/65 (EXEC_NI/XI/TM, + MVI/CI/CMI) | ◑ hybrid |
| 32 | 14023130F | PER‑PERI (preliminary phase) | 64/65→c8→d8/d9/da/db→dc→cc | ✅ cluster verified row-by-row; only residual is the PCOV status stub |
| 33 | 14023130G | TPER‑CPER external sequence | ca, a8, a9, aa, ab | ◑ states present; per-row needs higher-DPI recheck |
| 34 | 14023130₁ | CHANNEL‑**1** DATA TRANSFER phase | b8, b9, ea, eb | ◑ states present; write-back condition reworked (L207_output_writeback) |
| 35 | 14023130O | CHANNEL‑**3** DATA TRANSFER phase | (channel‑3 rSI sub-states) | ✗ not modelled |
| 36 | 14023130₁ | CHANNEL‑**2** DATA TRANSFER phase | rSI sub-states 0C/0E (in), 04/06 (compare), 02/03 (printer out, CE16), 0A/0B (end print) | ◑ recovered (docs/peripherals.md "CAN2 data-transfer phase"); wiring is Phase 3/5 |
| 38 | 14023130… | CMI‑CHI sequence | 64/65 (EXEC_CMI/EXEC_CI) | ◑ hybrid |
| 44‑45 | 14023130… | EXECUTIVE PHASE OP (data ops) | 64/65 (EXEC_SS + alu_*) | ◑ hybrid (SS executed by Mechanism B in e7/ef) |
(Render-pages 28/30 drawing-suffix letters were not legible at 300 DPI; the render-page is authoritative. Beyond render-45 the set continues with the remaining data-op sequences — PKS at render-46, etc.)
Legend: ✅ verified match · ◑ functionally correct but not a per-clock transcription, or partially transcribed · ⚠️ flagged for recheck · ✗ absent.
e2/e3, e0, e4, e6, e5, e7** (sheet 23): direct transcription; corroborated by the operand-fetch analysis and tests/alpha.c. The E4/E5 symmetry (not_RO07 gating CI60) is the key fix that makes the modifier reach V1; verified.ec/ed + ee/ef** (modified-address indexing): a hybrid fusion of the sheet-23 ED|EC/EF|EE boxes (one C-add instead of bit-serial low+high passes). Faithful in result and control flow; 4 unit tests in tests/exec.c.00 DISPLAY** (sheet 24): verified row-by-row — every CO/CI command and console-selector (AFxx) condition matches. One scan artifact: the chart's V3 → BO row reads [AF36], which is [AF30] (= RS_V3); gemu uses AF30.08 FORCING** (sheet 25): the command set (CO11/CO41/CO01, CO30/CO31, CI20/CI33, CI04/02/05/01/00/08/07/03/06/09, CI70..CI76 set-FIxx, CU00..CU17 from RO) matches the chart structure and tests/forcing.c passes. ⚠️ The exact firing brackets on three rows (the Mem→RO/AM→RO forcing reads: CO30, CO31, CI20/CI33) could not be aligned with confidence at 240–300 DPI — CO30 [AF51]/CO31 [AF41] in gemu vs. what looks like CO30 [—]/CO31 [AF51] on the foldout. Recheck against the physical foldout or a higher-quality scan before changing — forcing.c currently passes, so the live behaviour is constrained.Sheets 28, 29, 30, 31, 38, 44, 45 are the per-clock recipes for the beta phase (jumps, JS/JC/NOP/HLT/INS/ENS/LON/LOFF/LOLL, register ops, immediate logic ops, compares, and the SS data ops). gemu implements all of these in state_64_65 (and EXEC_SS for SS) via the hybrid mechanism: the MSL drives fetch/decode/sequence and routing, but the actual operation is performed once by a pure alu_* helper rather than transcribing the chart's per-clock datapath micro-steps. This is functionally correct and validated end-to-end (tests/exec.c, the funktionalcpu deck to 0x175a, cc/test.sh), but it is not cycle-accurate to these sheets.
Roadmap to close it: transcribe sheets 28/29/30/31/38/44/45 box-by-box into proper
state_64_65-family charts (or per-opcode beta states), replacing theEXEC_*one-shots with the charted CO/CI/CU steps. Large, must stay green againstexec.c+ the deck +cc. Lower priority than correctness, since the observable result already matches.
64/65→c8→d8→d9→da→db→⟨!FA05·!FA04⟩→dc→cc** and **80→⟨AINI⟩→c8 | e2/e3** (sheet 32): the full state graph and its diamonds are verified by tracing the CUxx future-state bit arithmetic (e.g. 0x80+CU06+CU03→0xC8; 0x64+CU07+CU15+CU03+CU12+CU10→0xC8; 0xC8+CU04→0xD8; 0xDC+CU14→0xCC). tests/initial-load.c locks the per-state register values along this path.c8, d8, d9, da, db, dc, cc were verified row-by-row against high-quality crops of sheet 32: every CO/CI/CE command row is present and the conditions match. Specifics confirmed:d8: PO-1→PO [FA05·‾DU93] = CO10/CO40/CO41/CO00 (CO00 gated FA05·!DU93); CE02 [‾FA05·‾FA04]; L12,1→RE = CI15/CI33/CE01. ✅cc: Set FI05 [PCOV·DU96·‾DU95 + FA00] = state_cc_TI06_CI75 exactly; RO→RA [‾PUC3] = CE00 [!PUC3]. The CC Mem→RO [‾AINI] overbar is legible here, confirming the c8 Mem→RO bracket is also ‾AINI (gemu not_AINI).dc: the manual's explicit channel-2 SI build Set S102,03 / Res S100,01 [L200·‾FA05] (CU02/03/10/11) is omitted in gemu, but is functionally equivalent: the base state 0xDC already carries low-nibble 1100, so CU20 forces the correct SI = 0xC without them. Defensive-only; not a bug.CA (TPER-CPER) / EA (SPER) is implemented via CUxx logic on the same signals, but the destinations depend on DU95/DU96/PCOV, and **PCOV is stubbed to 1** (signals.h) — so the EPER/SPER branch is only as faithful as the (unmodelled) channel peripheral status. This is the one real residual gap in the cluster.state_80 CO96 uses !FUL3 (matches the observed LOAD-2 → connector-3 name 0x00, locked by tests/initial-load.c load_2_button); c8 Mem→RO uses not_AINI (the PER path reads the descriptor; the chart bracket [AINI] is read as [‾AINI] with the overbar lost in the scan); and the db diamond proceeds to DC on !FA05·!FA04 TRUE (the operationally-correct busy-wait-exit polarity).ca, a8, a9, aa, ab** (sheet 33) and **b8, b9, ea, eb** (sheet 34): state coverage confirmed against the box labels. These carry in-code TODO/"missing manual page" notes and load-bearing stubs (DI82A/DI83A return constants; RENIA/RILIA/PCOV hardcoded), so they are the least cycle-faithful. They are constrained by tests/initial-load.c and the deck bootstrap, so changes are risky — recheck against the physical foldouts before editing.INTE = RINT·/MASC branch in e2/e3 already routed to 0xF0 (CU04), but F0 and the chain were empty slots. Added states F0→D2→D3→D0→D1→C2→C3→C0→C1→alpha (hybrid INT_* commands): F0–D1 save the PSR (status byte b5←FA04,b4←FA05,b0←FA06; then 0; then PO hi/lo) to the fixed store 0x0300; C2–C1 are the LPSR load of the new PSR from 0x0304, vectoring to its PO (the handler) and restoring FI04/05/06. RINT is acknowledged (cleared) in F0. Validated by tests/interrupt.c (save_and_vector, masked_does_not_divert). The path is dormant for the deck/other tests (RINT is never asserted there).0x9d): the interrupt uses the LPSR load states (C2–C1), but the LPSR 0x9d opcode is recognized and not decoded to enter them from beta.The flow-chart foldouts (sheets above, render-pg ~23-46) give the state graph and register transfers but are low-contrast and hard to read precisely. CPU[7] pages 61 onward carry the per-state timing tables — one (or two) per page, rotated 90° but with clean OCR — and these are the authoritative per-clock source that struct msl_timing_chart mirrors directly. Columns:
| Clock | Comando (command) | Equazione (firing equation) | Pin (board/loc) | Evento–Comment (register transfer) |
The Equazione column is the gold for fidelity: e.g. CO1011 = … / (DI12A0) maps to gemu's {clock, command, condition, additional}. Read them upright with:
The state-code box at the table head is the SO/SA hex (e.g. 1110 0000 = 0xE0).
Verified against these tables this session (full Clock↔Comando↔Equazione↔ Evento rows):
state_E0** (p61 top, code 1110 0000): 1:1 match — V2→NO, COUNT FROM 00, MEM→RO, NI→PO, NO→BO, RO1→NI1, RO2→NI2, RES AVER, NI→L1, Set S002, Reset S007 = CO12/CO41/CO30/CO00/(TO20 BO)/CI67/CI62/CI39/CI05/CU02/CU17, same order, DI17A0/DI12A0 gates matching, routing cond {FO06+FO07} = CU17.state_E2_E3** (p61 bottom): matched except the table lists four FI resets at TI06 (CI80 CI81 CI82 CI83 = Reset FI00/01/02/03) and gemu was missing **CI81 (Reset FI01)**. Fixed — added {TI06, CI81, 0} (FI01 is set only by forcing/b1, so this is a no-op for normal flow; deck + 244 tests stay green). Other gates confirmed: CI82 = EC50A0 {dRO=PER}, CU04 = EC53A0 {RINT·/FA06}, CU11 = (DI18A0), CI89 = EC51A0 {dRO=HLT + ASIN(...)} (gemu models the dRO=HLT term only).state_E4** (p62): the high-byte top-quartet gate CI60 = EC54A0 (an RO7-based decode) and CI65 = (DI19A0) confirm the bit-15 operand-fetch fix — gemu's not_RO07 on CI60 captures EC54A0's discriminating term, symmetric with E5. ✅ Caveat: the OCR renders CO1x as CO1O (letter O), so plain token-diffs miss CO-family commands — cross-check the rendered image when auditing E5/E6/E7 and the beta/peripheral tables. Next: walk pages 61+ row-by-row for the remaining states (E5/E6/E7, beta jumps/data, forcing 08, the peripheral cluster), image-confirming each like CI81.The scan in CPU[7] is a low-contrast foldout; bracket conditions and diamond labels often need a higher-quality scan or the physical foldout to read with confidence (consistent with the project's OCR page-image rule).