Amigan Software
Signetics-based Machines Coding/Gaming Guide
This document was written on 29/8/08, and last updated on 2/11/25,
by James Jacobs of Amigan Software.
Information herein is believed to be generally accurate, though some is
tentative. If you have anything to contribute, please
email us.
This page is part of Emerson Arcadia 2001 Central. Emulators, ROMs, manuals and other resources can be found there.
Emerson Arcadia 2001
├ Paddles
├ Graphics
├ Sound
├ Timing
├ Compiler 2001
├ Compatibility Notes
└ Gaming Guide
Interton VC 4000
├ Graphics
├ Compatibility Notes
└ Gaming Guide
Elektor TV Games Computer
├ Monitor BIOS
├ Signetics EOF (Elektor Object Format)
├ Magazine Articles
├ Compatibility Notes
└ Gaming Guide
PIPBUG/BINBUG-based machines
├ Teletype I/O
├ Cassette I/O
├ Papertape I/O
├ Printer I/O
├ Unarchived Software
├ BINBUG Hardware
├ BINBUG BIOS
├ Floppy Disk I/O
└ Game Help
Signetics Instructor 50
├ I/O Devices
├ USE BIOS
└ Game Help
Signetics TWIN
└ I/O Ports
Central Data 2650
├ Supervisor BIOS
├ DOSes
├ Unarchived Software
└ Game Help
PHUNSY
├ Mini-PHUNSY
└ Game Help
Ravensburger Selbstbaucomputer
├ Monitor BIOS
└ Game Help
MIKIT 2650
└ Game Help
Coin-ops
├
Malzak
├
Astro Wars & Galaxia
├
Laser Battle & Lazarian
├
Zaccaria Pinball for Android
├
Zaccaria Pinball for Switch
└
Zaccaria Pinball for Windows
Multiplatform
├ Comparative Tables
├ 2650 CPU
├ Project Numbers
├ Component Numbers
├ Programming Languages Overview
├ File Formats Overview
└ Signetics AOF (Absolute Object Format)

Emerson Arcadia 2001
| Region | Size | Emerson Arcadia 2001 | Tele-Fever | Palladium | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $0000..$0FFF | 4K | cartridge ROM | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1000..$10FF | 256 bytes | mirror of $1800..$18FF | CPU RAM | cartridge ROM | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1100..$11FF | 256 bytes | mirror of $1900..$19FF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1200..$12FF | 256 bytes | mirror of $1A00..$1AFF | CPU RAM | cartridge ROM | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1300..$13FF | 256 bytes | mirror of $1B00..$1BFF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1400..$17FF | 1K | mirror of $1000..$13FF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1800..$1AFF | 768 bytes | CPU+UVI RAM:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1B00..$1BFF | 256 bytes | mirror of $1900..$19FF | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1C00..$1FFF | 1K | mirror of $1800..$1BFF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $2000..$2FFF | 4K | cartridge ROM | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $3000..$3FFF | 4K | mirror of $1000..$1FFF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $4000..$4FFF | 4K | mirror of $0000..$0FFF? | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $5000..$5FFF | 4K | mirror of $1000..$1FFF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $6000..$6FFF | 4K | mirror of $0000..$0FFF? | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $7000..$7FFF | 4K | mirror of $1000..$1FFF | cartridge ROM | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
The architecture of the system is quite straightforward. A Signetics 2650 or 2650A CPU runs the programs and a Signetics 2637 UVI handles input and output. There are a pair of 2114 RAM chips. (There are also a few "glue" chips but these are irrelevant to programming (or emulating) the system.)
The ROM (game cartridge) is mapped to memory as already described. Execution starts from address $0000. (The CPU branches to address $0003 if an interrupt is generated at any time.) Addresses $1800..$1AFF are mapped to the UVI, I/O hardware and/or RAM. The game is not copied to RAM; it is instead run directly from ROM.
The chips may be in any state after a reset, and thus their contents should be cleared to known values at the start of the program to ensure proper operation.
The display is drawn by the UVI 60 times per second (for NTSC). The display is character-based (each character measuring 8*8 pixels), with programmable vertical and horizontal offsets. A choice of two resolutions (128*104 pixels or 16*13 characters, and 128*208 pixels or 16*26 characters) is available. The display is character-mapped, and thus does not need to be generated on the fly. There are 8 colours in the palette: black, white, red, green, blue, yellow, cyan and purple.
There are 56 characters stored in ROM, and 4 which are stored in RAM (and thus user-definable). Lowercase letters and most punctuation marks are not available. There is also a set of 64 "block graphics" characters which can be effectively "swapped in". Each character is displayed in a foreground and background colour. In mode 0 ("normal mode"), there are 4 foreground colours and 1 background colour available. In mode 1 ("board mode"), there are 2 foreground colours and 2 background colours available.
There are also four user-definable single-colour 8*8 sprites which can be freely positioned independently of the character display. The four sprite image definitions can also be used as user-defined graphics, just as with the four "true" user-defined graphics.
There are three buttons on the master console which can be detected by software. There are also twelve or more distinct buttons on each of the two controllers. Each controller also has a paddle, which can be digital or analogue.
There are two sound channels: a square wave channel (with 128 different frequencies possible), and a white noise channel (with 128 different modulations possible). There are 8 volume levels available.
Games are synchronized with the raster beam, as is usual for most systems. Many of the UVI registers can only be read or written at certain points in the frame. The vertical retrace status is available in the Sense pin of the CPU. (The Flag pin of the CPU can be used to invert the colours of all or part of the display.) All other UVI data is mapped to memory locations; specialized I/O commands are not used. The current character row being drawn by the UVI is available as a UVI register (mapped to a memory location). The current raster line being drawn by the UVI is not available but can of course be deduced by cycle counting. Horizontal retrace status is not available (but would deducable if bus DMA contention timings were known).
Arcadia-family BINs are stored and loaded as follows:
| ROM Size | On disk | In memory | ORG | ||
| 4K | $0000..$0FFF | 1st 4K chunk | $0000..$0FFF | 1st half of 1st page | $0000 |
| 8K | $1000..$1FFF | 2nd 4K chunk | $2000..$2FFF | 1st half of 2nd page | $0000 |
| 12K | $2000..$0FFF | 3rd 4K chunk | $4000..$4FFF | 1st half of 3rd page | $0000 |
| 16K | $3000..$0FFF | 4th 4K chunk | $6000..$6FFF | 1st half of 4th page | $0000 |
| 20K | $4000..$0FFF | 5th 4K chunk | $3000..$3FFF | 2nd half of 2nd page | $1000 |
| 24K | $5000..$0FFF | 6th 4K chunk | $5000..$5FFF | 2nd half of 3rd page | $1000 |
| 28K | $6000..$0FFF | 7th 4K chunk | $7000..$7FFF | 2nd half of 4th page | $1000 |
| 30K | $7000..$77FF | 2K chunk | $1000..$17FF | 3rd quarter of 1st page | $1000 |
| 31K | $7800..$7BFF | 1K chunk | $1C00..$1FFF | 8th eighth of 1st page | $1C00 |
Since no cartridges larger than 12K are known, this is somewhat
arbitrary beyond 12K and definitely arbitrary beyond 16K.
Although Palladium supports up to 31K ROMs (presumably),
Emerson and probably Tele-Fever support only up to 8K ROMs.
Cartridge RAM is not possible on any of these machines.
It is not possible to load from a cartridge into the
7th eighth of the 1st page ($1800..$1BFF); thus 32K ROMs are not possible.
Valid programs have certain startup requirements. Omitting these will not
cause problems on most emulators but will cause problems on the genuine
console. The machine at startup cannot be assumed to be in a known state;
you should explicitly initialize it. A soft reset does not reinitialize
the contents and status of the UVI, RAM, or even the CPU.
The fourth byte (ie. byte 3) should be $17, which is a RETC,UN
instruction. You should use bytes 0..2 to jump past that byte. You would
then typically clear then set the PSU and PSL, then wait, then clear
memory.
Your code can begin immediately following this code, at byte $20 (32).
Of course, some programs use a zero page jump table, so will have this
routine stored elsewhere.
Corrections to some common misconceptions about these machines:
There are 8 colours in the palette, not 9.
There is a clock of 3,579,545Hz at the 2621 USG (pin 12 clock). At pin
11 (PCK) there is a 3,579,545Hz clock which is connected to the 2637
UVI. At pin 10 (CK4) the 2650 is connected with a frequency of
894,886.25Hz, because the output divides the input frequency by 4.
The frequency measured at the input pin of the 2650 is still the
same.
Therefore, the effective speed is approx. 0.89MHz (approx. 3.58MHz÷4),
the same as the Interton VC 4000 has.
RAM is 1K (but Emerson-type has access to only half of this), not 28K.
"The Arcadia's makers didn't hook up the highest address line on
their pair of 2114 RAM chips; so what should be 1K of RAM is only
½K of RAM." - Ward Shrake.
Even Tele-Fever and Palladium don't appear to have any way to access more than 768 bytes
(the last 256 bytes should be mapped to $1B00..$1BFF but is not, and is thus wasted).
The are two sound channels (one tone and one noise), not one.
The "White MPT-03": there is no such system. This misconception
arises from erroneous stickers affixed to some MPT-03 games, saying: "For use
White Intelligent Game MPT-03". The intended meaning is "For use with Intelligent Game MPT-03".

Paddles
"The potentiometers [ie. P1PADDLE and P2PADDLE] read from $00 to $FE, and going to $FF when VRESET is low. I would assume the other Arcadia titles check to see if the potentiometer is [much] higher than $80 rather than simply looking for a value of $FF which doesn't happen on the real machine."
There are two paddles available. At any given moment they will either both contain X-coordinates or they will both contain Y-coordinates. Bit 6 of BGCOLOUR controls the paddle interpolation for both paddles. If this bit is 0, the Y-coordinates are available for reading. If it is 1, the X- coordinates are available. It seems that read the coordinates and then you set bit 6 of BGCOLOUR for which axis you want to read *next* frame. If you are only interested in one axis there is no need to flip the bit every frame, of course. You can only read the coordinates during vertical blank; reading them while the screen is being drawn will always give $FF.
Also, the Emerson and Schmid (at least) have ports to connect up to two additional hand controllers. The MPT-03 (at least) does not. No known games seem to support these. The hardware in question (unpluggable hand controllers) does not seem to have ever been officially produced, though it would presumably be trivial to develop such hardware, or to modify a "non-unpluggable" hand controller (by cutting the cable and adding a plug) for the purpose. The memory addresses at which these hand controllers would appear is not known (most likely somewhere in the $1909..$190F and/ or $19C0..$19F7 regions). Support for these hand controllers could be added to the emulators if the addresses were known.
The ranges used by each game for each direction are somewhat different. The values returned by the paddles are in fact different on each individual machine, and probably somewhat different for each individual hand controller. A value of $66 or $6A for a centred paddle appears most common.
| Game | Left/Up | Centred | Right/Down |
| Alien Invaders | $00..$35 | $36..$7D | $7E..$FE |
| Circus | $00..$3A | $3B..$93 | $94..$FE |
| Hobo | $00..$37 | $38..$98 | $99..$FE |
| Space Squadron | $00..$2F | $30..$A8 | $A9..$FE |
Only rough values are used in the table below:
X Y Paddle is being pushed
------------------------------------
$00 $00 up and left
$70 $00 up +---------+---------+---------+
$FE $00 up and right | 0,0 | $70,0 | $FE,0 |
$00 $70 left +---------+---------+---------+
$70 $70 centred | 0,$70 | $70,$70 | $FE,$70 |
$FE $70 right +---------+---------+---------+
$00 $FE down and left | 0,$FE | $70,$FE | $FE,$FE |
$70 $FE down +---------+---------+---------+
$FE $FE down and right
Note that these are read-once registers: they can only be read (once) during vblank, and can never be written.
$19FE: P2PADDLE: Right paddle status (8 bits) (read-once)
$19FF: P1PADDLE: Left paddle status (8 bits) (read-once)
During VRST, returns $00..$FE
When mux=0: about $00=up, about $70=middle, about $f1=down
When mux=1: about $07=left, about $70=middle, about $f1=right
While not in VRST, returns $FF

Graphics
3-bit colour codes (eg. as used for background and sprite colours) are as follows (referred to as "standard format" hereafter):
| GRB | With Flag off | With Flag on |
| %000 | White | Black |
| %001 | Yellow | Blue |
| %010 | Cyan | Red |
| %011 | Green | Purple (magenta) |
| %100 | Purple (magenta) | Green |
| %101 | Red | Cyan |
| %110 | Blue | Yellow |
| %111 | Black | White |
Other colours are not available but can of course be simulated by dithering or multiplexing across multiple pixels or frames, eg.:
| black | + white | = grey | |
| red | + white | = pink | |
| red | + yellow | = orange | |
| black | + yellow | = dark yellow | |
| black | + yellow | + red | = brown |
Colour artefacting also occurs on the real machine (even in PAL).
This is especially noticeable for eg.
Robot Killer walls and
Parashooter player sprite.
There are two colour modes, selected by the high bit (bit 7) of PITCH ($18FD). Mode 0 allows four character colours over one background colour. Mode 1 ("board mode") allows two character colours over two background colours.
In mode 0 (non-board mode):
bits 5..4 of BGCOLOUR are unused.
bit 3 of BGCOLOUR chooses foreground colour set (see table below).
bits 0..2 of BGCOLOUR are background colour (in standard format).
bits 5..0 of GFXMODE are unused.
In this mode, foreground colours are:
| Screen contents (with Flag off) | Screen contents (with Flag on) | |||||||
| $00..$3F | $40..$7F | $80..$BF | $C0..$FF | $00..$3F | $40..$7F | $80..$BF | $C0..$FF | |
| BGCOLOUR of %x,x,xx0,xxx | White | Cyan | Purple | Blue | Black | Red | Green | Yellow |
| BGCOLOUR of %x,x,xx1,xxx | Yellow | Green | Red | Black | Blue | Purple | Cyan | White |
In mode 1 (board mode):
bits 5..3 of BGCOLOUR are 2nd foreground colour (in standard format).
bits 0..2 of BGCOLOUR are outer background colour (in standard format).
bits 5..3 of GFXMODE are 1st foreground colour (in standard format).
bits 0..2 of GFXMODE are inner background colour (in standard format).
In this mode, foreground and background colours are:
| Screen contents of | ||||
| $00..$3F | $40..$7F | $80..$BF | $C0..$FF | |
| Foreground colour | 1st | 2nd | 1st | 2nd |
| Background colour | Inner | Outer | ||
In this mode, the screen is filled with the inner background colour, but is surrounded by a border filled with the outer background colour (although of course if the inner and outer background colours are the same the border will not be apparent). The two background and two foreground colours can all be chosen and used freely. Bit 7 of each character specify whether to use the inner (%0) or outer (%1) background colour for the background (off bits in the image definition). Bit 6 of each character specify whether to use the 1st (%0) or 2nd (%1) foreground colour for the foreground (on bits in the image definition).
Block graphics mode can be set by a $C0 at the start of a line, and terminated by a $40 at the start of a line, or controlled by the high bit (bit 7) of GFXMODE ($19F8). The format is:
22211100
22211100
22211100
22211100
55544433
55544433
55544433
55544433
where each digit is the bit position corresponding with that pixel. Bits 7..6 are the colour, as normal. Examples:
%xx000001 %xx000010 %xx000011 %xx000100 %xx000101 %xx000110
......## ...###.. ...##### ###..... ###...## ######..
......## ...###.. ...##### ###..... ###...## ######..
......## ...###.. ...##### ###..... ###...## ######..
......## ...###.. ...##### ###..... ###...## ######..
........ ........ ........ ........ ........ ........
........ ........ ........ ........ ........ ........
........ ........ ........ ........ ........ ........
........ ........ ........ ........ ........ ........
Character vs. block mode, and mode 0 vs. mode 1, are separate issues, and
thus the modes can be freely combined.
If you want low-res mode, you should set:
GFXMODE as %x,0,xxx,xxx
and BGCOLOUR as %0,x,xxx,xxx
If you want hi-res mode, you should set:
GFXMODE as %x,1,xxx,xxx
and BGCOLOUR as %1,x,xxx,xxx
Although it is possible to set them independently, it is generally pointless. The exception would be if you wanted low-resolution mode but did want the $1A00..$1ACF region drawn, and were using VSCROLL to vertically scroll the screen to reveal that area.
VSCROLL ($18FC) is "the complement of the number of lines from the
trailing edge of vertical drive to start character display". In other
words, you use this register to vertically scroll the entire display. All
8 bits of the register are used for this. Higher values indicate
positions towards the top of the screen, lower values indicate positions
towards the bottom of the screen (as for sprites).
$FF pushes the display to the top of the screen.
$ED seems to be used by most games.
$DF is the lowest which will show the entire display under MESS V2.
CHARLINE ($18FF) is a read-only hardware register.
Bits 7..4 are apparently unused? (these bits are always set?)
Bits 3..0 indicate the current character line (row) being rendered:
0..12 = which line
13 ($D) = end of DMA (ie. start of vertical blank)
14 ($E) = unused?
15 ($F) = beginning of DMA (ie. end of vertical blank)
Note that BGCOLOUR appears to be latched during the entire $F0..$FC
CHARLINE period; writes to it (to eg. change the background colour) do
not take immediate effect. (However, you can switch black/white (eg.
3D Bowling), red/cyan, green/purple (eg.
Ocean Battle) or blue/yellow (eg.
Dr. Slump,
Horse Racing,
Pleiades)
at any time by toggling the flag pin.)
Therefore, blue water with black road in
Frogger is not actually possible.
The horizontal resolution is 128 pixels; 16 tiles per row. The vertical resolution is either 104 (13 tiles per column) or 208 (26 tiles per column) pixels tall, Each tile is 8x8 in size. Graphics are character- based (ie. tile-based), not bitmapped. The screen is organized as a 16*13 or 16*26 grid of tiles, one byte per tile. There are also four freely positionable monochrome sprites. You can offset the display horizontally on a per-row (8 rasters) basis and vertically on a per-frame basis.
The "upper screen" is stored from $1800..$18CF; the top row is $1800.. $1810, the 2nd row is $1810..$181F, etc., to the 13th row from $18C0.. $18CF. In low-resolution mode this is all that is used. However, in high- resolution mode, the 13 rows of the "lower screen", stored from $1A00.. $1ACF, are also shown. These 208 "lower screen" bytes are available for use as extra RAM in low-resolution mode.
There are 64 characters In the character set. In non-block mode, these consist of 56 PDGs and 8 UDGs:
| Decimal | Hex | Description |
| 0 | $00 | built-in empty space (' ') |
| 1..2 | $01..$02 | built-in diagonal lines ('/', '\') |
| 3 | $03 | built-in solid ('■') |
| 4..7 | $04..$07 | built-in side lines |
| 8..11 | $08..$0B | built-in corners ('┐', '┌', '└', '┘') |
| 12..15 | $0C..$0F | built-in right-angled triangles ('◢', '◣', '◤', '◥') |
| 16..25 | $10..$19 | built-in numbers 0..9 |
| 26..51 | $1A..$33 | built-in uppercase letters A..Z |
| 52..55 | $34..$37 | built-in punctuation ('.', ',', '+', '$') |
| 56..59 | $38..$3B | sprites #0..#3 |
| 60..63 | $3C..$3F | user defined graphics #0..#3 |
$0123456789ABCDEF
-----------------
$00: /\#il_jwqasrtgf $00 : space
$10: 0123456789ABCDEF $01-$0F : graphics characters
$20: GHIJKLMNOPQRSTUV $38-$3B (zxcv): sprites 0-3
$30: WXYZ.,+$zxcvbnmh $3C-$3F (bnmh): user defined graphics 0-3
$00 ( ): ........ $01 (/): .......# $02 (\): #....... $03 (#): ########
........ ......#. .#...... ########
........ .....#.. ..#..... ########
........ ....#... ...#.... ########
........ ...#.... ....#... ########
........ ..#..... .....#.. ########
........ .#...... ......#. ########
........ #....... .......# ########
$04 (i): ######## $05 (l): ......## $06 (_): ........ $07 (j): ##......
######## ......## ........ ##......
........ ......## ........ ##......
........ ......## ........ ##......
........ ......## ........ ##......
........ ......## ........ ##......
........ ......## ######## ##......
........ ......## ######## ##......
$08 (w): ######## $09 (q): ######## $0A (a): ##...... $0B (s): ......##
######## ######## ##...... ......##
......## ##...... ##...... ......##
......## ##...... ##...... ......##
......## ##...... ##...... ......##
......## ##...... ##...... ......##
......## ##...... ######## ########
......## ##...... ######## ########
$0C (r): .......# $0D (t): #....... $0E (g): ######## $0F (f): ########
......## ##...... #######. .#######
.....### ###..... ######.. ..######
....#### ####.... #####... ...#####
...##### #####... ####.... ....####
..###### ######.. ###..... .....###
.####### #######. ##...... ......##
######## ######## #....... .......#
These occupy the low 6 bits (bits 5..0) of the byte. The upper 2 bits (bits 7..6) are used for the foreground colour, as previously described. Block mode is no different, except that a different set of image definitions is used (as previously described), and these occupy all characters 0..63; therefore sprite and UDG imagery cannot be used in block mode.
Strictly speaking there are eight UDGs (User Defined Graphics),
but the first four of them always have the same imagery as the four sprites.
The sprite UDGs (imagery at $1980..$199F) are characters
$38..$3B/$78..$7B/$B8..$BB/$F8..$FB.
The sprite colours, as stored in SPRnnCTRL, have no influence
on the colours of these when used as UDGs (only when used as actual
sprites); the colours used will be determined in the same
way as for any other tile.
The four dedicated UDGs (imagery $19A0..$19BF)
are characters $3C..$3F/$7C..$7F/$BC..$BF/$FC..$FF,
and are not usable as sprites.
Most consoles implement the Flag line (bit 7 of the PSU): while this is set, all colours are inverted. This even applies to sprites. The Tempest MPT-03 (and presumably all other MPT-03s) and Australian Emerson Arcadia 2001, for example, definitely do implement this. However, some consoles, such as the American Emerson Arcadia 2001, do not implement this and therefore the colours will never be inverted on such machines.
The Sense pin (bit 6 of the PSU) is read-only. It is set (to 1) as described elsewhere, to signify that the vertical retrace interval has begun, and cleared (to 0) to signify that the interval has ended.
Only 84 bytes are assigned for use exclusively as user RAM. There is a 32- byte block from $18D0..$18EF, a 4-byte block from $18F8..$18FB, and a 48- byte block from $1AD0..$1AFF. However, as the screen memory can be read and written to it is also possible to use that for storage; eg. in low- resolution the lower screen memory at $1A00..$1ACF will not be displayed and there is no reason in that case not to use it as 208 bytes of extra RAM, increasing the total available to 292 bytes.
There are 4 sprites, each measuring 8*8 pixels. Their colours and position are independent of the underlying character display. Similar to the way the character display can be vertically "squashed" or "stretched" with bit 7 of BGCOLOUR, each sprite can be vertically "squashed" or "stretched" independently of the character display and the other sprites (using bit 7 or 6 of SPRITESnnCTRL).
The foreground colour (1 bits in the image definition) of a sprite is chosen with bits 5..3 or 2..0 of SPRITESnnCTRL; all of the 8 colours are available. The background of a sprite (0 bits in the image definition) is transparent and thus never drawn (and not collision-checked either).
The coordinates of each sprite are relative to the bottom-left corner of the screen. That is to say, lower Y-coordinates are near the bottom of the screen, and higher Y-coordinates are near the top of the screen. Lower X- coordinates are near the left of the screen, and higher X-coordinates are near the right of the screen.
$18F0: SPRITE0Y
$18F1: SPRITE0X
$18F2: SPRITE1Y
$18F3: SPRITE1X
$18F4: SPRITE2Y
$18F5: SPRITE2X
$18F6: SPRITE3Y
$18F7: SPRITE3X (all read/write)
The horizontal and vertical coordinates of the four sprites will be
accessed by the UVI at DMA 15.
$18FC: VSCROLL (read/write)
The vertical offset will be accessed by the UVI at DMA 15.
$18FF: CHARLINE: Row status - last DMA number (4 bits) (read-only)
The status can be accessed anytime in the field when the microprocessor is not paused.
The sequence in 13-row mode is (from start to end of frame):
$FF, $F0, $F1, $F2, $F3, $F4, $F5, $F6, $F7, $F8, $F9, $FA, $FB, $FC, $FD, $FF
The sequence in 26-row mode is (from start to end of frame):
$FF, $F0, $F1, $F2, $F3, $F4, $F5, $F6, $F7, $F8, $F9, $FA, $FB, $FC, $F0, $F1, $F2, $F3, $F4, $F5, $F6, $F7, $F8, $F9, $FA, $FB, $FC, $FD, $FF
$19FA: SPRITES23CTRL (8 bits) (write-only)
Bit 7 : sprite #2 height (0=tall, 1=short)
Bit 6 : sprite #3 height (0=tall, 1=short)
Bits 5..3: sprite #2 colours
Bits 2..0: sprite #3 colours
$19FB: SPRITES01CTRL (8 bits) (write-only)
Bit 7 : sprite #0 height (0=tall, 1=short)
Bit 6 : sprite #1 height (0=tall, 1=short)
Bits 5..3: sprite #0 colours
Bits 2..0: sprite #1 colours
$19FC: BGCOLLIDE: Sprite collision with characters (4 bits) (read-once)
Bits 7..4: always %1111
Bit 3: sprite #3 collision with any character (%0=hit, %1=miss)
Bit 2: sprite #2 collision with any character (%0=hit, %1=miss)
Bit 1: sprite #1 collision with any character (%0=hit, %1=miss)
Bit 0: sprite #0 collision with any character (%0=hit, %1=miss)
It should be read during the vertical reset period.
The bits are reset (to 0) on collision and set (to 1) by reading or the trailing edge of VRST.
Each bit is set to 1 when the AND of the appropriate sprite and
background videos is high. Each bit is reset to 0 when accessed or at
the end of the vertical blanking period.
Waiting until CHARLINE is $FD or $FF does not seem to work reliably on
the real machine. It seems necessary to wait for the Sense bit (like
eg.
Combat does).
$19FD: SPRITECOLLIDE: Inter-sprite collision (6 bits) (read-once)
Bits 7..6: always %11
Bit 5: sprites #2/#3 collision (%0=hit, %1=miss)
Bit 4: sprites #1/#3 collision (%0=hit, %1=miss)
Bit 3: sprites #1/#2 collision (%0=hit, %1=miss)
Bit 2: sprites #0/#3 collision (%0=hit, %1=miss)
Bit 1: sprites #0/#2 collision (%0=hit, %1=miss)
Bit 0: sprites #0/#1 collision (%0=hit, %1=miss)
It should be read during the vertical reset period.
The bits are reset (to 0) on collision and set (to 1) by reading or the trailing edge of VRST.
Each bit is set to 0 when the AND of the appropriate two sprite
videos is high. Each bit is reset to 1 when accessed or at the end of
the vertical blanking period.
When multiple sprites are overlain atop one another, and the flag line is off, the RGB values of the overlapping pixels are ANDed together, ie.:
| 1st colour | 2nd colour | |||||||
| Black (rgb) | Blue (rgB) | Green (rGb) | Cyan (rGB) | Red (Rgb) | Purple (RgB) | Yellow (RGb) | White (RGB) | |
| Black (rgb) | rgb & rgb = rgb | rgb & rgB = rgb | rgb & rGb = rgb | rgb & rGB = rgb | rgb & Rgb = rgb | rgb & RgB = rgb | rgb & RGb = rgb | rgb & RGB = rgb |
| Blue (rgB) | rgB & rgb = rgb | rgB & rgB = rgB | rgB & rGb = rgb | rgB & rGB = rgB | rgB & Rgb = rgb | rgB & RgB = rgB | rgB & RGb = rgb | rgB & RGB = rgB |
| Green (rGb) | rGb & rgb = rgb | rGb & rgB = rgb | rGb & rGb = rGb | rGb & rGB = rGb | rGb & Rgb = rgb | rGb & RgB = rgb | rGb & RGb = rGb | rGb & RGB = rgb |
| Cyan (rGB) | rGB & rgb = rgb | rGB & rgB = rgB | rGB & rGb = rGb | rGB & rGB = rGB | rGB & Rgb = rgb | rGB & RgB = rgB | rGB & RGb = rGb | rGB & RGB = rGB |
| Red (Rgb) | Rgb & rgb = rgb | Rgb & rgB = rgb | Rgb & rGb = rgb | Rgb & rGB = rgb | Rgb & Rgb = Rgb | Rgb & RgB = Rgb | Rgb & RGb = Rgb | Rgb & RGB = Rgb |
| Purple (RgB) | RgB & rgb = rgb | RgB & rgB = rgB | RgB & rGb = rgb | RgB & rGB = rgB | RgB & Rgb = Rgb | RgB & RgB = RgB | RgB & RGb = Rgb | RgB & RGB = RgB |
| Yellow (RGb) | RGb & rgb = rgb | RGb & rgB = rgb | RGb & rGb = rGb | RGb & rGB = rGb | RGb & Rgb = Rgb | RGb & RgB = Rgb | RGb & RGb = RGb | RGb & RGB = RGb |
| White (RGB) | RGB & rgb = rgb | RGB & rgB = rgB | RGB & rGb = rGb | RGB & rGB = rGB | RGB & Rgb = Rgb | RGB & RgB = RbG | RGB & RGb = RGb | RGB & RGB = RGB |
Set bits are uppercase, clear bits are lowercase.
Sprite colours are only affected by the colours of other sprites,
never by the colours of the background or of PDG/UDG character tiles.
With the flag line on, the RGB values are OR'd together instead, ie.:
| 1st colour | 2nd colour | |||||||
| White (RGB) | Yellow (RGb) | Purple (RgB) | Red (Rgb) | Cyan (rGB) | Green (rGb) | Blue (rgB) | Black (rgb) | |
| White (RGB) | RGB | RGB = RGB | RGB | RGb = RGB | RGB | RgB = RGB | RGB | Rgb = RGB | RGB | rGB = RGB | RGB | rGb = RGB | RGB | rgB = RGB | RGB | rgb = RGB |
| Yellow (RGb) | RGb | RGB = RGB | RGb | RGb = RGb | RGb | RgB = RGB | RGb | Rgb = RGb | RGb | rGB = RGB | RGb | rGb = RGb | RGb | rgB = RGB | RGb | rgb = RGb |
| Purple (RgB) | RgB | RGB = RGB | RgB | RGb = RGB | RgB | RgB = RgB | RgB | Rgb = RgB | RgB | rGB = RGB | RgB | rGb = RGB | RgB | rgB = RgB | RgB | rgb = RgB |
| Red (Rgb) | Rgb | RGB = RGB | Rgb | RGb = RGb | Rgb | RgB = RgB | Rgb | Rgb = Rgb | Rgb | rGB = RGB | Rgb | rGb = RGb | Rgb | rgB = RgB | Rgb | rgb = Rgb |
| Cyan (rGB) | rGB | RGB = RGB | rGB | RGb = RGB | rGB | RgB = RGB | rGB | Rgb = RGB | rGB | rGB = rGB | rGB | rGb = rGB | rGB | rgB = rGB | rGB | rgb = rGB |
| Green (rGb) | rGb | RGB = RGB | rGb | RGb = RGb | rGb | RgB = RGB | rGb | Rgb = RGb | rGb | rGB = rGB | rGb | rGb = rGb | rGb | rgB = rGB | rGb | rgb = rGb |
| Blue (rgB) | rgB | RGB = RGB | rgB | RGb = RGB | rgB | RgB = RgB | rgB | Rgb = RgB | rgB | rGB = rGB | rgB | rGb = rGB | rgB | rgB = rgB | rgB | rgb = rgB |
| Black (rgb) | rgb | RGB = RGB | rgb | RGb = RGb | rgb | RgB = RgB | rgb | Rgb = Rgb | rgb | rGB = rGB | rgb | rGb = rGb | rgb | rgB = rgB | rgb | rgb = rgb |
Thus, the number of colour combinations yielding each final colour are:
| Final colour | For 1 sprite | For 2 sprites | For 3 sprites | For 4 sprites | |
| Flag off | Flag on | ||||
| Black | White | 1 (12.5%) | 27 (42.1875%) | 343 (~66.99219%) | 3375 (~82.39746%) |
| Blue | Yellow | 1 (12.5%) | 9 (14.0625%) | 49 (~9.57031%) | 225 (~5.49316%) |
| Green | Purple | 1 (12.5%) | 9 (14.0625%) | 49 (~9.57031%) | 225 (~5.49316%) |
| Cyan | Red | 1 (12.5%) | 3 (4.6875%) | 7 (~1.36719%) | 15 (~0.36621%) |
| Red | Cyan | 1 (12.5%) | 9 (14.0625%) | 49 (~9.57031%) | 225 (~5.49316%) |
| Purple | Green | 1 (12.5%) | 3 (4.6875%) | 7 (~1.36719%) | 15 (~0.36621%) |
| Yellow | Blue | 1 (12.5%) | 3 (4.6875%) | 7 (~1.36719%) | 15 (~0.36621%) |
| White | Black | 1 (12.5%) | 1 (1.5625%) | 1 (~0.19531%) | 1 (~0.02441%) |
| Total combinations | 8 (100%) | 64 (100%) | 512 (100%) | 4096 (100%) | |



Sound


This section also applies to
Interton and
Elektor, not just
Arcadia.
Here are the optimal PITCH register values for harmonic melodies:
| PITCH | Actual NTSC | Actual PAL | Ideal NTSC | Ideal PAL |
| $FF | 30.75781 | 30.5176 | b0 | ? |
| $FE | 30.87843 | 30.6373 | B0 (30.868 Hz) | ? |
| $FD | 31.00000 | 30.7579 | b0 | ? |
| $FC | 31.12253 | 30.8794 | b0 | B0 (30.868 Hz) |
| $FB | 31.24603 | 31.0020 | b0 | ? |
| $FA | 31.37052 | 31.1255 | b0 | ? |
| $F9 | 31.49600 | 31.2500 | b0 | ? |
| $F8 | 31.62249 | 31.3755 | b0 | ? |
| $F7 | 31.75000 | 31.5020 | c1 | ? |
| $F6 | 31.87854 | 31.6296 | c1 | ? |
| $F5 | 32.00813 | 31.7581 | c1 | ? |
| $F4 | 32.13877 | 31.8878 | c1 | ? |
| $F3 | 32.27049 | 32.0184 | c1 | ? |
| $F2 | 32.40329 | 32.1502 | c1 | ? |
| $F1 | 32.53719 | 32.2831 | c1 | ? |
| $F0 | 32.67220 | 32.4170 | C1 (32.703 Hz) | ? |
| $EF | 32.80833 | 32.5521 | c1 | ? |
| $EE | 32.94561 | 32.6883 | c1 | C1 (32.703 Hz) |
| $ED | 33.08403 | 32.8256 | c1 | ? |
| $EC | 33.22363 | 32.9641 | c1 | ? |
| $EB | 33.36441 | 33.1038 | c1 | ? |
| $EA | 33.50638 | 33.2447 | c1 | ? |
| $E9 | 33.64957 | 33.3868 | c#1/d♭1 | ? |
| $E8 | 33.79399 | 33.5300 | c#1/d♭1 | ? |
| $E7 | 33.93966 | 33.6746 | c#1/d♭1 | ? |
| $E6 | 34.08658 | 33.8203 | c#1/d♭1 | ? |
| $E5 | 34.23478 | 33.9674 | c#1/d♭1 | ? |
| $E4 | 34.38428 | 34.1157 | c#1/d♭1 | ? |
| $E3 | 34.53509 | 34.2654 | c#1/d♭1 | ? |
| $E2 | 34.68723 | 34.4163 | C#1/D♭1 (34.648 Hz) | ? |
| $E1 | 34.84071 | 34.5686 | c#1/d♭1 | ? |
| $E0 | 34.99556 | 34.7222 | c#1/d♭1 | C#1 (34.648 Hz) |
| $DF | 35.15179 | 34.8772 | c#1/d♭1 | ? |
| $DE | 35.30942 | 35.0336 | c#1/d♭1 | ? |
| $DD | 35.46847 | 35.1914 | c#1/d♭1 | ? |
| $DC | 35.62896 | 35.3507 | d1 | ? |
| $DB | 35.79091 | 35.5114 | d1 | ? |
| $DA | 35.95434 | 35.6735 | d1 | ? |
| $D9 | 36.11927 | 35.8372 | d1 | ? |
| $D8 | 36.28571 | 36.0023 | d1 | ? |
| $D7 | 36.45370 | 36.1690 | d1 | ? |
| $D6 | 36.62326 | 36.3372 | D1 (36.708 Hz) | ? |
| $D5 | 36.79439 | 36.5070 | d1 | ? |
| $D4 | 36.96714 | 36.6784 | d1 | D1 (36.708 Hz) |
| $D3 | 37.14151 | 36.8514 | d1 | ? |
| $D2 | 37.31754 | 37.0261 | d1 | ? |
| $D1 | 37.49524 | 37.2024 | d1 | ? |
| $D0 | 37.67464 | 37.3804 | d1 | ? |
| $CF | 37.85577 | 37.5601 | d#1/e♭1 | ? |
| $CE | 38.03865 | 37.7415 | d#1/e♭1 | ? |
| $CD | 38.22330 | 37.9248 | d#1/e♭1 | ? |
| $CC | 38.40976 | 38.1098 | d#1/e♭1 | ? |
| $CB | 38.59804 | 38.2966 | d#1/e♭1 | ? |
| $CA | 38.78818 | 38.4852 | d#1/e♭1 | ? |
| $C9 | 38.98020 | 38.6757 | D#1/e♭1 (38.891 Hz) | ? |
| $C8 | 39.17413 | 38.8682 | d#1/e♭1 | D#1/E♭1 (38.891 Hz) |
| $C7 | 39.37000 | 39.0625 | d#1/e♭1 | ? |
| $C6 | 39.56784 | 39.2588 | d#1/e♭1 | ? |
| $C5 | 39.76768 | 39.4571 | d#1/e♭1 | ? |
| $C4 | 39.96954 | 39.6574 | d#1/e♭1 | ? |
| $C3 | 40.17347 | 39.8597 | e1 | ? |
| $C2 | 40.37949 | 40.0641 | e1 | ? |
| $C1 | 40.58763 | 40.2706 | e1 | ? |
| $C0 | 40.79793 | 40.4793 | e1 | ? |
| $BF | 41.01042 | 40.6901 | e1 | ? |
| $BE | 41.22513 | 40.9031 | E1 (41.203 Hz) | ? |
| $BD | 41.44210 | 41.1184 | e1 | E1 (41.203 Hz) |
| $BC | 41.66138 | 41.3360 | e1 | ? |
| $BB | 41.88298 | 41.5559 | e1 | ? |
| $BA | 42.10695 | 41.7781 | e1 | ? |
| $B9 | 42.33333 | 42.0027 | e1 | ? |
| $B8 | 42.56216 | 42.2297 | f1 | ? |
| $B7 | 42.79348 | 42.4592 | f1 | ? |
| $B6 | 43.02732 | 42.6913 | f1 | ? |
| $B5 | 43.26374 | 42.9258 | f1 | ? |
| $B4 | 43.50276 | 43.1630 | f1 | ? |
| $B3 | 43.74445 | 43.4028 | F1 (43.654 Hz) | ? |
| $B2 | 43.98883 | 43.6453 | f1 | F1 (43.654 Hz) |
| $B1 | 44.23595 | 43.8904 | f1 | ? |
| $B0 | 44.48587 | 44.1384 | f1 | ? |
| $AF | 44.73864 | 44.3892 | f1 | ? |
| $AE | 44.99429 | 44.6429 | f1 | ? |
| $AD | 45.25287 | 44.8994 | f#1/g♭1 | ? |
| $AC | 45.51445 | 45.1590 | f#1/g♭1 | ? |
| $AB | 45.77907 | 45.4215 | f#1/g♭1 | ? |
| $AA | 46.04678 | 45.6871 | f#1/g♭1 | ? |
| $A9 | 46.31765 | 45.9559 | F#1/G♭1 (46.249 Hz) | ? |
| $A8 | 46.59172 | 46.2278 | f#1/g♭1 | F#1/G♭1 (46.249 Hz) |
| $A7 | 46.86905 | 46.5030 | f#1/g♭1 | ? |
| $A6 | 47.14970 | 46.7814 | f#1/g♭1 | ? |
| $A5 | 47.43373 | 47.0633 | f#1/g♭1 | ? |
| $A4 | 47.72121 | 47.3485 | f#1/g♭1 | ? |
| $A3 | 48.01220 | 47.6372 | g1 | ? |
| $A2 | 48.30675 | 47.9294 | g1 | ? |
| $A1 | 48.60494 | 48.2253 | g1 | ? |
| $A0 | 48.90683 | 48.5248 | G1 (48.999 Hz) | ? |
| $9F | 49.21250 | 48.8281 | g1 | ? |
| $9E | 49.52201 | 49.1352 | g1 | G1 (48.999 Hz) |
| $9D | 49.83544 | 49.4462 | g1 | ? |
| $9C | 50.15287 | 49.7611 | g1 | ? |
| $9B | 50.47436 | 50.0801 | g1 | ? |
| $9A | 50.80000 | 50.4032 | g#1/a♭1 | ? |
| $99 | 51.12987 | 50.7305 | g#1/a♭1 | ? |
| $98 | 51.46405 | 51.0621 | g#1/a♭1 | ? |
| $97 | 51.80263 | 51.3980 | G#1/A♭1 (51.913 Hz) | ? |
| $96 | 52.14569 | 51.7384 | g#1/a♭1 | ? |
| $95 | 52.49333 | 52.0833 | g#1/a♭1 | G#1/A♭1 (51.913 Hz) |
| $94 | 52.84564 | 52.4329 | g#1/a♭1 | ? |
| $93 | 53.20270 | 52.7872 | g#1/a♭1 | ? |
| $92 | 53.56462 | 53.1463 | a1 | ? |
| $91 | 53.93151 | 53.5103 | a1 | ? |
| $90 | 54.30345 | 53.8793 | a1 | ? |
| $8F | 54.68056 | 54.2535 | a1 | ? |
| $8E | 55.06294 | 54.6329 | A1 (55.000 Hz) | ? |
| $8D | 55.45070 | 55.0176 | a1 | A1 (55.000 Hz) |
| $8C | 55.84397 | 55.4078 | a1 | ? |
| $8B | 56.24286 | 55.8036 | a1 | ? |
| $8A | 56.64748 | 56.2050 | a1 | ? |
| $89 | 57.05797 | 56.6123 | a#1/b♭1 | ? |
| $88 | 57.47445 | 57.0255 | a#1/b♭1 | ? |
| $87 | 57.89706 | 57.4449 | a#1/b♭1 | ? |
| $86 | 58.32593 | 57.8704 | A#1/B♭1 (58.270 Hz) | ? |
| $85 | 58.76119 | 58.3022 | a#1/b♭1 | A#1/B♭1 (58.270 Hz) |
| $84 | 59.20301 | 58.7406 | a#1/b♭1 | ? |
| $83 | 59.65152 | 59.1856 | a#1/b♭1 | ? |
| $82 | 60.10687 | 59.6374 | a#1/b♭1 | ? |
| $81 | 60.56923 | 60.0962 | a#1/b♭1 | ? |
| $80 | 61.03876 | 60.5620 | b1 | ? |
| $7F | 61.52 | 61.0352 | B1 (61.735 Hz) | b1 |
| $7E | 62.00 | 61.5157 | b1 | B1 (61.735 Hz) |
| $7D | 62.49 | 62.0040 | b1 | b1 |
| $7C | 62.99 | 62.5000 | b1 | b1 |
| $7B | 63.50 | 63.0040 | b1 | b1 |
| $7A | 64.02 | 63.5163 | c2 | c2 |
| $79 | 64.54 | 64.0369 | c2 | c2 |
| $78 | 65.07 | 64.5661 | c2 | c2 |
| $77 | 65.62 | 65.1042 | C2 (65.406 Hz) | c2 |
| $76 | 66.17 | 65.6513 | c2 | C2 (65.406 Hz) |
| $75 | 66.73 | 66.2076 | c2 | ? |
| $74 | 67.30 | 66.7735 | c2 | ? |
| $73 | 67.88 | 67.3491 | c#2/d♭2 | ? |
| $72 | 68.47 | 67.9348 | c#2/d♭2 | ? |
| $71 | 69.07 | 68.5307 | c#2/d♭2 | ? |
| $70 | 69.68 | 69.1372 | C#2/D♭2 (69.296 Hz) | C#2/D♭2 (69.296 Hz) |
| $6F | 70.30 | 69.7545 | c#2/d♭2 | ? |
| $6E | 70.94 | 70.3829 | c#2/d♭2 | ? |
| $6D | 71.58 | 71.0227 | d2 | ? |
| $6C | 72.24 | 71.6743 | d2 | ? |
| $6B | 72.91 | 72.3380 | D2 (73.416 Hz) | ? |
| $6A | 73.59 | 73.0140 | d2 | ? |
| $69 | 74.28 | 73.7028 | d2 | D2 (73.416 Hz) |
| $68 | 74.99 | 74.4048 | d2 | ? |
| $67 | 75.71 | 75.1202 | d2 | ? |
| $66 | 76.45 | 75.8495 | d#2/e♭2 | ? |
| $65 | 77.20 | 76.5931 | d#2/e♭2 | ? |
| $64 | 77.96 | 77.3515 | D#2/E♭2 (77.782 Hz) | D#2/E♭2 (77.782 Hz) |
| $63 | 78.74 | 78.1250 | d#2/e♭2 | ? |
| $62 | 79.54 | 78.9141 | d#2/e♭2 | ? |
| $61 | 80.35 | 79.7194 | e2 | ? |
| $60 | 81.18 | 80.5412 | e2 | ? |
| $5F | 82.02 | 81.3802 | E2 (82.407 Hz) | ? |
| $5E | 82.88 | 82.2368 | e2 | E2 (82.407 Hz) |
| $5D | 83.77 | 83.1117 | e2 | ? |
| $5C | 84.67 | 84.0054 | e2 | ? |
| $5B | 85.59 | 84.9185 | f2 | ? |
| $5A | 86.53 | 85.8516 | f2 | ? |
| $59 | 87.49 | 86.8056 | F2 (87.307 Hz) | ? |
| $58 | 88.47 | 87.7809 | f2 | F2 (87.307 Hz) |
| $57 | 89.48 | 88.7784 | f2 | ? |
| $56 | 90.51 | 89.7989 | f#2 | ? |
| $55 | 91.56 | 90.8430 | f#2 | ? |
| $54 | 92.64 | 91.9118 | F#2/G♭2 (92.499 Hz) | ? |
| $53 | 93.74 | 93.0060 | f#2 | F#2/G♭2 (92.499 Hz) |
| $52 | 94.87 | 94.1265 | g2 | ? |
| $51 | 96.02 | 95.2744 | g2 | ? |
| $50 | 97.21 | 96.4506 | g2 | ? |
| $4F | 98.42 | 97.6563 | G2 (97.999 Hz) | G2 (97.999 Hz) |
| $4E | 99.67 | 98.8924 | g2 | ? |
| $4D | 100.95 | 100.160 | g#2/a♭2 | ? |
| $4C | 102.26 | 101.461 | g#2/a♭2 | ? |
| $4B | 103.61 | 102.796 | G#2/A♭2 (103.826 Hz) | ? |
| $4A | 104.99 | 104.167 | g#2/a♭2 | G#2/A♭2 (103.826 Hz) |
| $49 | 106.41 | 105.574 | g#2/a♭2 | ? |
| $48 | 107.86 | 107.021 | a2 | ? |
| $47 | 109.36 | 108.507 | a2 | ? |
| $46 | 110.90 | 110.035 | A2 (110.000 Hz) | A2 (110.000 Hz) |
| $45 | 112.49 | 111.607 | a2 | ? |
| $44 | 114.12 | 113.225 | a#2/b♭2 | ? |
| $43 | 115.79 | 114.890 | a#2/b♭2 | ? |
| $42 | 117.52 | 116.604 | A#2/B♭2 (116.541 Hz) | A#2/B♭2 (116.541 Hz) |
| $41 | 119.30 | 118.371 | a#2/b♭2 | ? |
| $40 | 121.14 | 120.192 | a#2/b♭2 | ? |
| $3F | 123.03 | 122.070 | B2 (123.471 Hz) | B2 (123.471 Hz) |
| $3E | 124.98 | 124.008 | b2 | ? |
| $3D | 127.00 | 126.008 | c3 | ? |
| $3C | 129.08 | 128.074 | c3 | ? |
| $3B | 131.23 | 130.208 | C3 (130.813 Hz) | C3 (130.813 Hz) |
| $3A | 133.46 | 132.415 | c#3 | - |
| $39 | 135.76 | 134.698 | c#3 | - |
| $38 | 138.14 | 137.061 | C#3/D♭3 (138.591 Hz) | ? |
| $37 | 140.61 | 139.509 | c#3 | C#3/D♭3 (138.591 Hz) |
| $36 | 143.16 | 142.045 | d3 | ? |
| $35 | 145.81 | 144.676 | D3 (146.832 Hz) | ? |
| $34 | 148.57 | 147.406 | d3 | D3 (146.832 Hz) |
| $33 | 151.42 | 150.240 | d3 | ? |
| $32 | 154.39 | 153.186 | d#3/e♭3 | ? |
| $31 | 157.48 | 156.250 | D#3/E♭3 (155.563 Hz) | |
| $30 | 160.69 | 159.439 | d#3/e♭3 | ? |
| $2F | 164.04 | 162.760 | E3 (164.814 Hz) | ? |
| $2E | 167.53 | 166.223 | e3 | E3 (164.814 Hz) |
| $2D | 171.17 | 169.837 | f3 | ? |
| $2C | 174.98 | 173.611 | F3 (174.614 Hz) | |
| $2B | 178.95 | 177.557 | f3 | ? |
| $2A | 183.12 | 181.686 | F#3/G♭3 (184.997 Hz) | ? |
| $29 | 187.48 | 186.012 | f#3/g♭3 | F#3/G♭3 (184.997 Hz) |
| $28 | 192.05 | 190.549 | g3 | ? |
| $27 | 196.85 | 195.313 | G3 (195.998 Hz) | |
| $26 | 201.90 | 200.321 | g3 | ? |
| $25 | 207.21 | 205.592 | G#3/A♭3 (207.652 Hz) | |
| $24 | 212.81 | 211.149 | g#3/a♭3 | ? |
| $23 | 218.72 | 217.014 | A3 (220.000 Hz) | |
| $22 | 224.97 | 223.214 | a3 | ? |
| $21 | 231.59 | 229.779 | A#3/B♭3 (233.082 Hz) | |
| $20 | 238.61 | 236.742 | a#3/b♭3 | ? |
| $1F | 246.06 | 244.141 | B3 (246.942 Hz) | |
| $1E | 254.00 | 252.016 | b3 | ? |
| $1D | 262.47 | 260.417 | C4 (261.626 Hz) | |
| $1C | 271.52 | 269.397 | c#4/d♭4 | ? |
| $1B | 281.21 | 279.018 | C#4/D♭4 (277.183 Hz) | |
| $1A | 291.63 | 289.352 | D4 (293.665 Hz) | |
| $19 | 302.84 | 300.481 | d4 | ? |
| $18 | 314.96 | 312.500 | D#4/E♭4 (311.127 Hz) | |
| $17 | 328.08 | 325.521 | E4 (329.628 Hz) | |
| $16 | 342.35 | 339.674 | f4 | ? |
| $15 | 357.91 | 355.114 | F4 (349.228 Hz) | |
| $14 | 374.95 | 372.024 | F#4/G♭4 (369.994 Hz) | |
| $13 | 393.70 | 390.625 | G4 (391.995 Hz) | |
| $12 | 414.42 | 411.184 | G#4/A♭4 (415.305 Hz) | |
| $11 | 437.44 | 434.028 | A4 (440.000 Hz) | |
| $10 | 463.18 | 459.559 | A#4/B♭4 (466.164 Hz) | |
| $0F | 492.12 | 488.281 | B4 (493.883 Hz) | |
| $0E | 524.93 | 520.833 | C5 (523.251 Hz) | |
| $0D | 562.43 | 558.036 | C#5/D♭5 (554.365 Hz) | |
| D5 (587.33 Hz) | ||||
| $0C | 605.69 | 600.962 | D#5 (622.254 Hz) | D5 (587.33 Hz) |
| $0B | 656.17 | 651.042 | E5 (659.255 Hz) | |
| $0A | 715.82 | 710.227 | F5 (698.456 Hz) | |
| F#5/G♭5 (739.99 Hz) | ||||
| $09 | 787.40 | 781.250 | G5 (783.991) | |
| G#5/A♭5 (830.61 Hz) | ||||
| $08 | 874.89 | 868.056 | A5 (880.000 Hz) | |
| A#5/B♭5 (932.30 Hz) | ||||
| $07 | 984.25 | 976.562 | B5 (987.767 Hz) | |
| C6 (1046.50 Hz) | ||||
| $06 | 1124.86 | 1116.071 | C#6/D♭6 (1108.731 Hz) | |
| D6 (1174.70 Hz) | ||||
| D#6/E♭6 (1244.50 Hz) | ||||
| $05 | 1312.33 | 1302.083 | E6 (1318.510 Hz) | |
| F6 (1396.90 Hz) | ||||
| F#6/G♭6 (1480.00 Hz) | ||||
| $04 | 1574.80 | 1562.500 | G6 (1567.982 Hz) | |
| G#6/A♭6 (1661.20 Hz) | ||||
| A6 (1760.00 Hz) | ||||
| A#6/B♭6 (1864.66 Hz) | ||||
| $03 | 1968.50 | 1953.125 | B6 (1975.53 Hz) | |
| C7 (2093.00 Hz) | ||||
| C#7/D♭7 (2217.46 Hz) | ||||
| D7 (2349.32 Hz) | ||||
| D#7/E♭7 (2489.02 Hz) | ||||
| $02 | 2624.67 | 2604.167 | E7 (2637.02 Hz) | |
| F7 (2793.83 Hz) | ||||
| F#7/G♭7 (2959.96 Hz) | ||||
| G7 (3135.96 Hz) | ||||
| G#7/A♭7 (3322.44 Hz) | ||||
| A7 (3520.00 Hz) | ||||
| A#7/B♭7 (3729.31 Hz) | ||||
| $01 | 3937.00 | 3906.250 | B7 (3951.07 Hz) | |
| $00 | Rest | |||
This should assist in illustrating why tones are off-key.
High-pitched notes (3..1) cause aliasing effects.
Arcadia can only play notes $00..$7F (shown in green).
Interton and
Elektor can play all notes $00..$FF (shown in yellow and green).
Note that as all
Intertons and
Elektors are PAL, the NTSC information for $80..$FF is only of theoretical interest.
For
Arcadia, the algorithm for tone generation is:
frequency = 7874 ÷ ((PITCH & %01111111) + 1); (NTSC)
frequency = 7812½ ÷ ((PITCH & %01111111) + 1); (PAL )
frequency = 2 * ((PITCH & %01111111) + 1) * horizontal line period;
For
Interton/
Elektor, the algorithm for tone generation is:
frequency = 7874 ÷ ( PITCH + 1); (NTSC)
frequency = 7812½ ÷ ( PITCH + 1); (PAL )
frequency = 2 * ( PITCH + 1) * horizontal line period;
so for NTSC $01, at 3937 Hz:
1÷3937 = 2 * (1 + 1) * horizontal line period
0.000254 = 4 * horizontal line period
0.0000635 = horizontal line period
and for NTSC $02, at ~2624 Hz:
1÷2624 = 2 * (2 + 1) * horizontal line period
0.000381 = 6 * horizontal line period
0.0000635 = horizontal line period
and for PAL $01, at 3906.250 Hz:
1÷3906.25 = 2 * (1 + 1) * horizontal line period
0.000256 = 4 * horizontal line period
0.000064 = horizontal line period
Thus, horizontal line period is 63.5 µS (NTSC) or 64 µS (PAL).
The table below is similar to the table above, but is laid out as a piano-style keyboard (with unusable keys omitted):
| Low Notes | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Note | B0 | C1 | C#1 D♭1 | D1 | D#1 E♭1 | E1 | F1 | F#1 G♭1 | G1 | G#1 A♭1 | A1 | A#1 B♭1 | B1 | C2 | C#2
D♭2 | D2 | D#2
E♭2 | E2 | F2 | F#2
G♭2 | G2 | G#2
A♭2 | A2 | A#2
B♭2 | B2 | C3 | C#3
D♭3 | D3 | D#3
E♭3 | E3 | F3 | F#3
G♭3 | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| NTSC PITCH | FE | F0 | E2 | D6 | C9 | BE | B3 | A9 | A0 | 97 | 8E | 86 | 7F | 77 | 70 | 6D | 64 | 5F | 59 | 54 | 4F | 4B | 46 | 42 | 3F | 3B | 38 | 35 | 31 | 2F | 2C | 2A | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| PAL PITCH | FC | EE | E0 | D4 | C8 | BD | B2 | A8 | 9E | 95 | 8D | 85 | 7E | 76 | 70 | 69 | 64 | 5E | 58 | 53 | 4F | 4A | 46 | 42 | 3F | 3B | 37 | 34 | 31 | 2E | 2C | 29
| High Notes
| Note
| G3
| G#3
| A♭3 A3
| A#3
| B♭3 B3
| C4
| C#4
| D♭4 D4
| D#4
| E♭4 E4
| F4
| F#4
| G♭4 G4
| G#4
| A♭4 A4
| A#4
| B♭4 B4
| C5
| C#5
| D♭5 D5
| D#5
| E♭5 E5
| F5
| G5
| A5
| B5
| C#6
| D♭6 E6
| G6
| B6
| E7
| B7
| NTSC PITCH
| 27
| 25
| 23
| 21
| 1F
| 1D
| 1B
| 1A
| 18
| 17
| 15
| 14
| 13
| 12
| 11
| 10
| 0F
| 0E
| 0D
| -
| 0C
| 0B
| 0A
| 09
| 08
| 07
| 06
| 05
| 04
| 03
| 02
| 01
| PAL PITCH
| 27
| 25
| 23
| 21
| 1F
| 1D
| 1B
| 1A
| 18
| 17
| 15
| 14
| 13
| 12
| 11
| 10
| 0F
| 0E
| 0D
| 0C
| -
| 0B
| 0A
| 09
| 08
| 07
| 06
| 05
| 04
| 03
| 02
| 01
| | ||||||||||||||||||||||||||||||||
The noise generator works much like the tone generator. As with the tone
generator, it only ever generates square waves (ie. the speaker is only
ever at maximum plus or maximum minus (here designated as +127 and -128
for convenience), not any intermediate values). However, whereas the tone
generator flips from +127 to -127 and vice versa at regular, predictable
intervals, the noise generator only flips, on average, on half of those
occasions; the rest of the time, the output value is held steady.
Or, to put it a different way, the difference is that whenever the tone
generator would flip the amplitude (eg. change from -127 to +127 or vice
versa), the amplitude will be randomly chosen to be -127 or +127.
Eg. if you set a noise of $40, this is equivalent to 121.1385Hz. So,
approximately every 121th of a second, the following pseudocode would be
executed:
if ((rand() % 2) == 0) value = 127; else value = -127;
So, whereas a tone waveform might look like this:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | |
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | |
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | |
|_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |_| |
a noise waveform of the same frequency might look like this:
___ _ _ ___ _____ _ _ _ ___ _ ___ _
| | | | | | | | | | | | | | | | | | | | | | | | | |
| | | | | | | | | | | | | | | | | | | | | | | | | |
| | | | | | | | | | | | | | | | | | | | | | | | | |
|_| |_| |_| |___| |_| |_| |_| |___| |___| |_| |_| |_| |_|
The higher the pitch (frequency), the more random the noise will sound. Ie. lower values are more regular and rhythmic.
Sample values are (with acknowledgements to Tom Pittman):
$7F = static
$10 = rocket exhaust
$04 = machine gun
$02 = engine racing
$00 = silence
Note that the preceding discussion of the noise hardware also applies to systems such as the Interton VC 4000 and expanded Elektor TVGC.
Arcadia sound is inferior to Interton sound in three ways:
Lowest pitches are not possible on Arcadia;
Only 8 volume levels on Arcadia instead of 16; and
No explosion circuit ("banger").

Timing
Anything in this section that contradicts the information here is probably wrong.
3D Bowling waits for approximately 284 CPU cycles for a scanline?
Circus exhibits different behaviour depending on whether the vertical
blanking interval takes <= 621 CPU cycles or not (<= approx. 32 rastlines).
Green background (or purple, if theres is no Flag pin) is when the CPU is slow and the UVI is fast (vblank done in not many CPU cycles) (NTSC),
Black background (or white, if there is no Flag pin) is when the CPU is fast and the UVI is slow (vblank takes a lot of CPU cycles) (PAL).
NTSC vertical blank takes 18.91667 CPU cycles per rastline * 20 rastlines = 378.3' CPU cycles per vblank.
PAL vertical blank takes 18.91667 CPU cycles per rastline * 43 rastlines = 813.41681 CPU cycles per vblank.
This is based on information found in the 2637 UVI manual:
While drawing the top area (ie. VOFFSET area):
DMA is $FF.
UVI and RAM are accessible.
Sense is probably pulled low now.
Sprite coordinates and vertical offset are read now.
UDGs may be changed now.
While drawing main area:
DMA is $F0..$FC.
UVI is inaccessible.
RAM may be locked out.
Sense is pulled low now if it wasn't already.
After drawing main area, now it is drawing the bottom area (ie. rest of VOFFSET area):
DMA is $FD.
UVI is accessible.
Sense is maybe pulled high now.
RAM may be locked out.
Now it is doing 3 more (undisplayed) rasters. During this time the
electron beam is actually moving diagonally up the screen in preparation
for drawing the next frame (ie. this is the true vertical retrace
interval):
UVI and RAM are accessible.
DMA is $FF.
Sense is pulled high now if it wasn't already.
UDGs may be changed now.
To wait for the START of the vertical blank period, the usual method is:
WAITVBLSTART:
;start of loop
tpsu $80 ;test bits %10000000 of PSU;
bcfr,eq WAITVBLSTART ;if != goto WAITVBLSTART;
;end of loop
To wait for the END of the vertical blank period, the usual method is:
WAITVBLEND:
;start of loop
tpsu $80 ;test bits %10000000 of PSU;
bctr,eq WAITVBLEND ;if == goto WAITVBLEND;
;end of loop
So, BCFR is used when waiting for the START of vertical blank (ie. the END of the display frame), and BCTR is used when waiting for the END of vertical blank (ie. the START of the display frame).
To wait for a specified CHARLINE, the usual method is:
WAITLINE:
;start of loop
loda,r0 CHARLINE
andi,r0 $0F
comi,r0 $03 ;change the operand according to desired line
bcfr,eq WAITLINE
;end of loop
The example above waits until line 3 (ie. CHARLINE == $F3). Change the operand of the COMI instruction as appropriate for other lines.

Compiler 2001
Here is a dissassembly of sync_example.bin, with corresponding source
lines shown.
Note that the raw output of Compiler 2001 is encrypted and requires
decrypting into ordinary 2650 code. Also, its output is buggy, as
indicated below.
set sound off (actual): set sound off (corrected):
set noise off (actual): set noise off (corrected):
set text mode (actual): set text mode (corrected):
set hi resolution:
set vertical scroll n:
set horizontal scroll n:
set extended colour mode off set extended colour mode off
repeat:
cls:
EORZ r0 ;$00
LODI,r1 $D0 ;$01..$02
cls_1:
STRA,r0 $17FF,r1 ;$03..$05
BDRR,r1 CLS_1 ;$06..$07
EORZ r0 ;$08 (useless!)
LODI,r1 $D0 ;$09..$0A
cls_2:
STRA,r0 $19FF,r1 ;$0B..$0D
BDRR,r1 CLS_2 ;$0E..$0F
LODA,r3 PITCH ;$10..$12 LODA,r3 VOLUME
ANDI,r3 $F7 ;$13..$14 ANDI,r3 $F7
STRA,r3 VOLUME
LODA,r3 PITCH ;$15..$17 LODA,r3 VOLUME
ANDI,r3 $EF ;$18..$19 ANDI,r3 $10
STRA,r3 VOLUME
LODA,r0 GFXMODE ;$1A..$1C LODA,r0 GFXMODE
ANDI,r0 $7F ;$1D..$1E ANDI,r0 $7F
STRA,r0 $1918 ;$1F..$21 STRA,r0 GFXMODE
LODA,r3 BGCOLOUR ;$22..$24
IORI,r3 $80 ;$25..$26
STRA,r3 BGCOLOUR ;$27..$29
LODI,r3 n ;$2A..$2B
STRA,r3 VSCROLL ;$2C..$2E
LODA,r3 VOLUME ;$2F..$31
ANDI,r3 $0F ;$32..$33
IORI,r3 n ;$34..$35
STRA,r3 VOLUME ;$36..$38
(actual): (corrected):
LODA,r3 PITCH ;$39..$3B LODA,r3 PITCH
ANDI,r3 $7F ;$3C..$3D ANDI,r3 $7F
STRA,r3 PITCH
set screen colour green
set screen colour blue
forever
LODA,r3 BGCOLOUR
ANDI,r3 $F8
IORI,r3 green [3]
STRA,r3 BGCOLOUR
LODA,r3 BGCOLOUR
ANDI,r3 $F8
IORI,r3 blue [6]
STRA,r3 BGCOLOUR
BCTA,un repeat
Built-in constants:
| WHITE=0 |
| YELLOW=1 |
| CYAN=2 |
| GREEN=3 |
| PURPLE=4 |
| RED=5 |
| BLUE=6 |
| BLACK=7 |
Label styles:
label code
label
.label
Comment styles:
REM comment
/comment
Endless loop styles:
DO
body
LOOP
REPEAT
body
FOREVER
Miscellaneous:
| : | statement separator (same as in BASIC) |
| variable=value | LODI,r0 value
STRA,r0 variable |
| constant=value | constant EQU value |
Statements:
| BRANCH address | BCTA,un |
| BRANCH SUB address | BSTA,un |
| RETURN | RETC,un |
| DIM variable AS BYTE|INTEGER | ? |
| CLS | ? |
| SCREEN colour | Same as SET SCREEN COLOR colour? |
| SET SOUND OFF | ? |
| SET NOISE OFF | ? |
| SET TEXT MODE | ? |
| SET HI RESOLUTION | ? |
| SET VERTICAL SCROLL 0..255 | ? |
| SET HORIZONTAL SCROLL 0..7 | ? |
| SET EXTENDED COLOR MODE ON|OFF | ? |
| SET SCREEN COLOR colour | Same as SCREEN colour? |
| SYNC | ? |
| SYNC number | DMA line, eg. 1 or 25 |

Compatibility Notes
Observations from a real Australian PAL Emerson Arcadia 2001:
The Flag line is enabled (so colours can be inverted by games).
Joysticks are purely digital; no analog is possible. They are self-centring.
The plastic tab on the left side of cartridge slot must be snapped off for
compatibility with American Emerson Arcadia 2001 cartridges.
The paddles return the following values for their extreme and centred positions:
| Left player | Right player | ||||
| $07,$00 | $68,$00 | $FE,$00 | $07,$00 | $63..$64,$00 | $FE,$00 |
| $07,$70..$71 | $68,$70..$71 | $FE,$70..$71 | $07,$69..$6A | $63..$64,$69..$6A | $FE,$69..$6A |
| $07,$FE | $68,$FE | $FE,$FE | $07,$FE | $63..$64,$FE | $FE,$FE |
8 Sprites:
It doesn't work on the emulator or the real machine.
It needs $7Ds at addresses $E and $12 changed to $7Cs.
Failing that, it is dependent on the value of r0.
Circus:
It has a black background on a real Australian PAL Emerson Arcadia
(means PAL detected; green background means NTSC detected).
Counter, Message:
These don't fully initialize the system at startup.
You will need to issue a POKE VSCROLL $FF command to be able to see the on-screen text.
Frogger 1.4::
On Ami/WinArcadia 34.32, at least, on NTSC, on level 2, collision
detection is bad (empty road killing frog sometimes, snakes taking
two lives). It is unknown whether this happens on a real NTSC machine.
On a real PAL machine, at least, some movement clicks are inaudible
(presumably their duration is too short).
Multiplex::
P1PADDLE is always reading as $FF; presumably it is being read at the
wrong moment. (So the sprite constantly moves down and right).
Target 1::
It doesn't work on the emulator or the real machine.
He is turning on block mode for some reason; it works if that is changed
(change byte $0009 from $BF to $03).
Tester1..3::
See the relevant source code (TESTER?.ASM in the Homebrews Pack) for results.
VScroll::
The range of values that are completely visible on the TV is $CC..$FB.
Definite emulator compatibility issues as at V34.32 (these don't happen on real machine):
Doraemon: There is sometimes a blank line between your head and body when moving down.
Dr. Slump: There is sometimes a flickering horizontal line at the top of the "tea-can" and "tea-can man".
Parashooter,
Pleiades: The sound is different.
Possible emulator compatibility issues (not retested on emulator nor real machine recently):
Baseball: There are very occasional graphics/collision problems?
Jungler: Some of your bullets are ineffective?
Parashooter: There are graphics glitches when losing a life?
Space Attack: Enemies glitch sometimes when attacking?
Space Raiders,
Space Squadron:
These occasionally "drop" frames, especially when the action is busy?
Player bullets sometimes pass through aliens (the yellow enemies)?
Does it ever happen when we are a reasonable distance from them, and alive? If so, it is an emulator bug.

Interton VC 4000
See also the document here.
Also, parts of the
Elektor section are applicable. For sound programming, see here.
There are four different cartridge configurations known:
| Region | Size | 2K ROM/EPROM + 0K RAM | 4K ROM/EPROM + 0K RAM | 4K ROM + 1K RAM1 | 6K ROM + 1K RAM2 |
| $0000..$07FF | 2K | game ROM/EPROM | |||
| $0800..$0FFF | 2K | unused | game ROM/EPROM | ||
| $1000..$13FF | 1K | unused | cartridge RAM | game ROM/EPROM | |
| $1400..$15FF | ½K | unused | mirror of $1000..$11FF | ||
| $1600..$17FF | ½K | mirror of $1E00..$1FFF | mirror of $1E00..$1FFF (obscures ½K of game ROM/EPROM) | ||
| $1800..$1BFF | 1K | unused | mirror of $1000..$13FF | cartridge RAM | |
| $1C00..$1DFF | ½K | unused | mirror of $1400..$15FF | mirror of $1800..$19FF | |
| $1E00..$1EFF | ¼K | I/O area | |||
| $1F00..$1FFF | ¼K | PVI area (see Elektor memory map, except that randomizers are never present)
| |||
| $2000..$7FFF | 24K | 3 mirrors of $0000..$1FFF | |||
1Backgammon, Chess 1 and Draughts only.
2Chess 2 only.
Note that writes to $1E80..$1EFF affect the NOISE register ($1E80). Reads
within this range are handled as shown above. (This applies to both
Interton and
Elektor.)
Vertical and horizontal grid registers are of course usable as ordinary
user RAM by games which do not use the grid (such games do not set the
"grid/background enable" flag in BGCOLOUR, or set the grid colour to be
the same as the screen (background) colour).
Some addresses are read-once.
"The object descriptor areas and background definition range can also be
read at all times in the normal way. In the I/O and control section,
however, reading data causes that location to be reset to $00." - 2636 PVI
datasheet.
The Flag pin of the PSU (in the 2650 CPU) controls the paddle
interpolation (ie. whether horizontal or vertical).
The following code fragments relevant to the white-noise generator are given in the "TV Games Computer" book, p. 187:
;"sound off"
;"PVI sound on"
;"noise (ie. explosion) on"
;"sound off"
;NOISE = 0;
eorz r0
stra,r0 NOISE
;NOISE = 0;
lodi,r0 0
stra,r0 NOISE
;NOISE = 4;
lodi,r0 4
stra,r0 NOISE
;NOISE = $10;
lodi,r0 $10
stra,r0 NOISE
Note that "noise", in the discussion in that chapter, refers to the explosion generator ("banger"), not the white-noise generator.
Interton-family BINs are stored and loaded as follows:
| ROM Size | On disk | In memory | ORG | ||
| 2K | $0000..$07FF | 1st 2K chunk | $0000..$07FF | 1st quarter of 1st page | $0000 |
| 4K | $0800..$0FFF | 2nd 2K chunk | $0000..$07FF | 2nd quarter of 1st page | $0000 |
| 6K | $1000..$17FF* | 3rd 2K chunk | $1000..$15FF* | 9th..11th sixteenths of 2nd page | $0000 |
* The last 512 bytes of a 6K ROM
($1600..$17FF) is obscured by the mirror there of $1E00..$1FFF;
therefore the usable size is limited to 5½K.
Since games are not able to be any larger you don't need to worry about
CPU page issues because you will only be using the first page anyway.
Corrections to some common misconceptions about these machines:
The Interton VC 4000 was supposedly made from 1974 but not sold
until 1978. However, the Signetics 2650 CPU was only made from 1975;
therefore, the Interton VC 4000 could not have been made from 1974.
There are 16 colours, not 9.
There are no multicoloured sprites. All sprites are single-colour
(although the same effect can of course be achieved by superimposing
multiple sprites atop one another).

Graphics
3-bit colour codes (eg. as used for background and sprite colours) are:
| RGB | Bright colour | Dark colour |
| %000 | Black #1 | Black #2 |
| %001 | Blue | Dark blue |
| %010 | Green | Dark green |
| %011 | Cyan | Dark cyan |
| %100 | Red | Dark red |
| %101 | Purple (magenta) | Dark purple |
| %110 | Yellow | Dark yellow |
| %111 | White | Grey |
Colours 0..7 are fullbrite (FB). Colours 8..15 are halfbrite (HB).
For halfbrite machines:
Background colour is: 8 + (bits 2..0 of BGCOLOUR ) (ie. 8..15)
Grid colour is: 8 + ((bits 6..4 of BGCOLOUR ) >> 4) (ie. 8..15)
For fullbrite machines:
Background colour is: (bits 2..0 of BGCOLOUR ) (ie. 0..7)
Grid colour is: ((bits 6..4 of BGCOLOUR ) >> 4) (ie. 0..7)
For all machines:
Digit colours are: 7 - ((bits 6..4 of BGCOLOUR ) >> 4) (ie. 0..7)
Sprite #0 colours are: 7 - ((bits 5..3 of SPR01COLOURS) >> 3) (ie. 0..7)
Sprite #1 colours are: 7 - (bits 2..0 of SPR01COLOURS) (ie. 0..7)
Sprite #2 colours are: 7 - ((bits 5..3 of SPR23COLOURS) >> 3) (ie. 0..7)
Sprite #3 colours are: 7 - (bits 2..0 of SPR23COLOURS) (ie. 0..7)
The digit colour is always dependent on the grid colour, and vice versa, as shown:
| BGCOLOUR | Grid (fullbrite) | Grid (halfbrite) | Digits |
| %x000xxxx | Black #1 | Black #2 | White |
| %x001xxxx | Blue | Dark blue | Yellow |
| %x010xxxx | Green | Dark green | Purple |
| %x011xxxx | Cyan | Dark cyan | Red |
| %x100xxxx | Red | Dark red | Cyan |
| %x101xxxx | Purple | Dark purple | Green |
| %x110xxxx | Yellow | Dark yellow | Blue |
| %x111xxxx | White | Grey | Black #1 |
Some
Interton VC 4000 family members, such as the Fountain,
apparently use fullbrite mode rather than halfbrite mode.
Elektor TVGC seems to use halfbrite mode for at least some games, eg.
Catapult. Fullbrite mode may also perhaps be available.
Each digit is 12*20 pixels.
Digit Y-area is 20..39 and/or 200..219, depending on SCORECTRL.
1st digit X-area is 60.. 71.
2nd digit X-area is 76.. 87.
3rd digit X-area is 92..103 or 108..119, depending on SCORECTRL.
4th digit X-area is 108..119 or 124..135, depending on SCORECTRL.
Table of bits controlling which grid segments are lit:
| Addresses (hexadecimal) | Row | Set | |||||||||||||||
| 1F80:7 | 1F80:6 | 1F80:5 | 1F80:4 | 1F80:3 | 1F80:2 | 1F80:1 | 1F80:0 | 1F81:7 | 1F81:6 | 1F81:5 | 1F81:4 | 1F81:3 | 1F81:2 | 1F81:1 | 1F81:0 | 0 (raster 20) | 1 |
| 1 | |||||||||||||||||
| 1F82:7 | 1F82:6 | 1F82:5 | 1F82:4 | 1F82:3 | 1F82:2 | 1F82:1 | 1F82:0 | 1F83:7 | 1F83:6 | 1F83:5 | 1F83:4 | 1F83:3 | 1F83:2 | 1F83:1 | 1F83:0 | 2 | 2a |
| 3 | |||||||||||||||||
| 4 | |||||||||||||||||
| 5 | |||||||||||||||||
| 6 | |||||||||||||||||
| 7 | |||||||||||||||||
| 8 | |||||||||||||||||
| 9 | |||||||||||||||||
| 10 | |||||||||||||||||
| 11 | 2b | ||||||||||||||||
| 12 | |||||||||||||||||
| 13 | |||||||||||||||||
| 14 | |||||||||||||||||
| 15 | |||||||||||||||||
| 16 | |||||||||||||||||
| 17 | |||||||||||||||||
| 18 | |||||||||||||||||
| 19 (raster 39) | |||||||||||||||||
| : : : | |||||||||||||||||
| 1FA4:7 | 1FA4:6 | 1FA4:5 | 1FA4:4 | 1FA4:3 | 1FA4:2 | 1FA4:1 | 1FA4:0 | 1FA5:7 | 1FA5:6 | 1FA5:5 | 1FA5:4 | 1FA5:3 | 1FA5:2 | 1FA5:1 | 1FA5:0 | 180 (raster 200) | 19 |
| 181 | |||||||||||||||||
| 1FA6:7 | 1FA6:6 | 1FA6:5 | 1FA6:4 | 1FA6:3 | 1FA6:2 | 1FA6:1 | 1FA6:0 | 1FA7:7 | 1FA7:6 | 1FA7:5 | 1FA7:4 | 1FA7:3 | 1FA7:2 | 1FA7:1 | 1FA7:0 | 182 | 20a |
| 183 | |||||||||||||||||
| 184 | |||||||||||||||||
| 185 | |||||||||||||||||
| 186 | |||||||||||||||||
| 187 | |||||||||||||||||
| 188 | |||||||||||||||||
| 189 | |||||||||||||||||
| 190 | |||||||||||||||||
| 191 | 20b | ||||||||||||||||
| 192 | |||||||||||||||||
| 193 | |||||||||||||||||
| 194 | |||||||||||||||||
| 195 | |||||||||||||||||
| 196 | |||||||||||||||||
| 197 | |||||||||||||||||
| 198 | |||||||||||||||||
| 199 (raster 219) | |||||||||||||||||
Table of bits controlling segment widths:
$1FA8:7..6: %00 or %10 = 1x width for sets 1.. 4 (except where overridden by $1FA8:5..0)
%01 = 2x width for sets 1.. 4 (except where overridden by $1FA8:5..0)
%11 = 4x width for sets 1.. 4 (except where overridden by $1FA8:5..0)
$1FA8:5: %0 = 1x/2x/4x width for set 4b (depending on $1FA8:7..6)
%1 = 8x width for set 4b
$1FA8:4: %0 = 1x/2x/4x width for set 4a (depending on $1FA8:7..6)
%1 = 8x width for set 4a
$1FA8:3: %0 = 1x/2x/4x width for set 3 (depending on $1FA8:7..6)
%1 = 8x width for set 3
$1FA8:2: %0 = 1x/2x/4x width for set 2b (depending on $1FA8:7..6)
%1 = 8x width for set 2b
$1FA8:1: %0 = 1x/2x/4x width for set 2a (depending on $1FA8:7..6)
%1 = 8x width for set 2a
$1FA8:0: %0 = 1x/2x/4x width for set 1 (depending on $1FA8:7..6)
%1 = 8x width for set 1
: : :
$1FAC:7..6: %00 or %10 = 1x width for sets 17..20 (except where overridden by $1FAC:5..0)
%01 = 2x width for sets 17..20 (except where overridden by $1FAC:5..0)
%11 = 4x width for sets 17..20 (except where overridden by $1FAC:5..0)
$1FAC:5: %0 = 1x/2x/4x width for set 20b (depending on $1FAC:7..6)
%1 = 8x width for set 20b
$1FAC:4: %0 = 1x/2x/4x width for set 20a (depending on $1FAC:7..6)
%1 = 8x width for set 20a
$1FAC:3: %0 = 1x/2x/4x width for set 19 (depending on $1FAC:7..6)
%1 = 8x width for set 19
$1FAC:2: %0 = 1x/2x/4x width for set 18b (depending on $1FAC:7..6)
%1 = 8x width for set 18b
$1FAC:1: %0 = 1x/2x/4x width for set 18a (depending on $1FAC:7..6)
%1 = 8x width for set 18a
$1FAC:0: %0 = 1x/2x/4x width for set 17 (depending on $1FAC:7..6)
%1 = 8x width for set 17
The top left corner of the grid section is at 81,63 in 2621 USG coordinates or 32,20 in 2636 PVI coordinates.
The PVI datasheet is wrong to imply that the last raster in which imagery
is displayable is 251 (p. 6), ie. 252 visible rasters. Experimental
results (eg.
Elektor Tester1) show that at least 268 rasters are visible
(for PAL, of course).
The "Tools|Screen editor" function of the emulator is an easy way to experiment and to create game displays.
SPRITEnAX: "If SPRITEnAX is changed during the time that the corresponding object video is being displayed, the portion of the object not yet displayed will be displaced to the new horizontal position." Ie. it is resampled every pixel (at least whilst the sprite is being displayed).
SPRITEnAY: "The value of SPRITEnAY is 'remembered' at the trailing edge of VRST. Thus, if SPRITEnAY is changed during the active scan, the vertical object position change will not be effective until the next active scan." Ie. it is sampled once per frame (at the end of vertical blank).
SPRITEnBY is when to redraw (reuse) the sprite:
$FF means 0 rastlines gap
$00 means 1 rastline gap
$01 means 2 rastlines gap
$02 means 3 rastlines gap
$FC means 253 rastlines gap
$FD means "never" (but this register will still be reexamined each rastline?)
$FE means "never" (but this register will still be reexamined each rastline?)
According to the 2636 PVI datasheet:
Sprite X = SPRITEAXn + 1 (assuming leftmost clock is 0)
Sprite Y = SPRITEAYn + 1 (assuming topmost raster is 0)
SPRITEAXn of >= 228 is not displayed.
SPRITEAYn of >= 253 is not displayed.
SPRITEAXn is not cached (or is cached during HRST).
SPRITEAYn must be changed by (ie. it is cached at) the end of VRST.
SPRITEBXn is cached during HRST.
SPRITEBY is sampled just prior to displaying the last line of the
(original or duplicate) object. That sampling presumably wouldn't affect
the last line itself.
"The interrupt generation occurs during the horizontal sync at the end of the last line of the sprite display." - Manfred Schneider.
2636 PVI datasheet example:
Sprite #1 ( original) is shown at 42..49, 36.. 45.
Either 250 or 251 is the last displayable rastline.
SPRITE2AX = 62
Sprite #2 ( original) is shown at 62..69, 20.. 29.
SPRITE1AX = 42
SPRITE1AY = 36
SPRITE1BX = 30
SPRITE1BY = 9 (10 line gap)
Sprite #1 ( 1st dup.) is shown at 30..37, 56.. 65.
Sprite #1 ( 2nd dup.) is shown at 30..37, 76.. 85.
Sprite #1 ( 3rd dup.) is shown at 30..37, 96..105.
Sprite #1 ( 4th dup.) is shown at 30..37,116..125.
Sprite #1 ( 5th dup.) is shown at 30..37,136..145.
Sprite #1 ( 6th dup.) is shown at 30..37,156..165.
Sprite #1 ( 7th dup.) is shown at 30..37,176..185.
Sprite #1 ( 8th dup.) is shown at 30..37,196..205.
Sprite #1 ( 9th dup.) is shown at 30..37,216..225.
Sprite #1 (10th dup.) is shown at 30..37,236..245.
SPRITE2AY = 20
SPRITE2BX = 88
SPRITE2BY = 27 (28 line gap)
Sprite #2 ( 1st dup.) is shown at 88..95, 58.. 67.
Sprite #2 ( 2nd dup.) is shown at 88..95, 96..105.
Sprite #2 ( 3rd dup.) is shown at 88..95,134..143.
Sprite #2 ( 4th dup.) is shown at 88..95,172..181.
Sprite #2 ( 5th dup.) is shown at 88..95,210..219.
Sprite #2 ( 6th dup.) is shown at 88..95,248..250/251?

Compatibility Notes
Resolved questions:
Q. Are mid-sprite changes to SPRITEnAX effective?
A.
Tester2 confirms that they are.
"If SPRITEnAX is changed during the time that the corresponding object
video is being displayed, the portion of the object not yet displayed will
be displaced to the new horizontal position." - PVI manual, p. 5.
"Unlike SPRITEnAX and SPRITEnAY, SPRITEnBX and SPRITEnBY may be changed
during the scan and such changes will be effected on the current scan." -
PVI manual, p. 5.
The first statement is correct. The second statement should be amended to
"Unlike SPRITEnAY, SPRITEnBX and SPRITEnBY may be changed during the scan
and such changes will be effected on the current scan."
Q.. How do sprite coordinates relate to eg. grid coordinates?
eg. SPRITEnAX=31,SPRITEnAY=19 is top left of grid (according to 2636 PVI
datasheet, p. 5)
or is above and to the left of the top left grid (according to 2636 PVI
datasheet, p. 6)
A. SPRITEnAY = $FF aligns the sprite to raster 0
SPRITEnAY = $00 aligns the sprite to raster 1
SPRITEnAY = $01 aligns the sprite to raster 2
etc. This is demonstrated by eg.
Interton Blackjack.
Unresolved questions:
exactly what the latching behaviour of the PVI is (eg. exactly how
often and at what x,y points in the frame the PVI reads or writes each
of its registers);
bus contention (each time the PVI accesses memory the CPU is blocked
and enters a wait state if it tries to access memory at the same
time);
exact state of the system at startup (values of the memory contents).
mirroring: what actual addresses reads and writes are resolved to;
exactly what happens when the CPU executes each of the undocumented CPU
instructions.
Test programs could be written in the future to answer those questions.
Interton VC 4000: assumed behaviour is that the low nybbles of CONSOLE and PnFOOKEYS are set to %1111, the same as is proven to occur on an Elektor TVGC.
Gridlines that are the same colour as the background (ie. invisible) don't register collisions. This seems to be the correct behaviour.
Based on the behaviour of Catapult, Destroyer and Submarine+Racing (all
for
Elektor), the real PVI probably doesn't involve the
digits in collision detection.
ESS-011-7-OmegaLanding and ESS-011-D-Painting
seem to expect collisions at the far left (< 9) to not register.
"Unlike SPRITEnAX and SPRITEnAY, SPRITEnBX and SPRITEnBY may
be changed during the scan [(frame)] and such changes will be effected
on the current scan [(frame)]. SPRITEnBX is sampled during each HRST
[(horizontal reset)]. Thus, if SPRITEnBX is changed during the
display of a duplicate, a portion of the object will be
displaced horizontally. For proper operation, SPRITEnBX should
be changed only *after* the 'Object Video Completion' status
bit [in BGCOLLIDE] indicates completion of the object.
SPRITEnBY is sampled just prior to displaying the last line of
the object. To effect a change in the vertical offset to the
next duplicate, SPRITEnBY must be changed *before* the 'Object
Video Completion' status bit [in BGCOLLIDE] indicates
completion of the object." - PVI manual, p. 5. But that is incorrect as
Circus relies on being able to change SPRITEnAX so that the balloons are
drawn properly.
Munch & Crunch:
"I have found a bug in Munch & Crunch which no doubt explains the
occasional glitches I have seen. It's in my simplistic return from
interrupt:
loda,r0 STOREPSL
lpsl
loda,r0 STORER0
rete,un
The problem of course is that the condition code in the PSL gets changed
by the final load instruction. Having looked at other disassemblies I must
say that I'm impressed by how the AND $C0 to a copy of PSL correctly
restores the condition code. The condition codes were obviously carefully
chosen when designing the processor.
From Blackjack:
loda,r0 PRESERVEPSL ;r0 = PRESERVEPSL
strz r4 ;r4 = r0;
lpsl ;PSL = r0; restores psl but with bank 1
loda,r0 PRESERVER0 ;restore r0
andi,r4 $C0
cpsl $10 ;Bank 0
rete,un
The 2650B with its LDPL and STPL instructions was a big improvement." - Derek Andrews.

Elektor TV Games Computer
Parts of the
Interton section are applicable. For sound programming, see here.
These are the components of a basic system:
motherboard
power supply
keyboard
joysticks
speaker
cassette interface
cassette deck
VHF/UHF modulator
TV (television)
There are two versions of the Elektor TV Games Computer: the standard "base" or "basic" version, and the "extended" version. The base and extended versions have 2K and 5K of RAM, respectively. There are also other differences. The Rapid Loading Games (RLG) expansion can be added to the extended version. They use the following memory maps:
| Region | Size | Basic | Expanded | Expanded + RLG | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $0000..$07FF | 2K | monitor (BIOS) ROM | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $0800..$08BF | 192 bytes | motherboard RAM (for use by monitor):
$08B9..$08BA: interrupt vector $08BE..$08BF: start address of game | motherboard RAM (used for data for RLG load routine) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $08C0..$0FFF | 1856 bytes | motherboard RAM (for storage of and use by games) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1000..$15FF | 1½K | unused | motherboard RAM (for storage of and use by games) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1600..$17FF | ½K | mirror of $1E00..$1FFF | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1800..$187F | 128 bytes | mirror of $1D00..$1D7F | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1880..$189F | 32 bytes | 8 mirrors of $1D9C..$1D9F (input lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $18A0..$18BF | 32 bytes | 8 mirrors of $1DBC..$1DBF (input lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $18C0..$18DF | 32 bytes | 8 mirrors of $1DDC..$1DDF (output lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $18E0..$18FF | 32 bytes | 8 mirrors of $1DFC..$1DFF (output lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1900..$197F | 128 bytes | mirror of $1D00..$1D7F | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1980..$199B | 28 bytes | 7 mirrors of $1D9C..$1D9F (input lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $199C..$199F | 4 bytes | mirror of $1D9C..$1D9F (input lines 0..3) | if (*($73E) == $19) mirror of $1D9C..$1D9F (obscures 4 bytes of RAM)
if (*($73E) == $1D) motherboard RAM (for storage of and use by games) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $19A0..$19BB | 28 bytes | 7 mirrors of $1DBC..$1DBF (input lines 4..7) | motherboard RAM (for storage of and use by games) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $19BC..$19BF | 4 bytes | mirror of $1DBC..$1DBF (input lines 4..7) | if (*($73E) == $19) mirror of $1DBC..$1DBF (obscures 4 bytes of RAM)
if (*($73E) == $1D) motherboard RAM (for storage of and use by games) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $19C0..$19DF | 32 bytes | 8 mirrors of $1DDC..$1DDF (output lines 0..3) | motherboard RAM (for storage of and use by games) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $19E0..$19FF | 32 bytes | 8 mirrors of $1DFC..$1DFF (output lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1A00..$1A7F | 128 bytes | mirror of $1D00..$1D7F | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1A80..$1A9F | 32 bytes | 8 mirrors of $1D9C..$1D9F (input lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1AA0..$1ABF | 32 bytes | 8 mirrors of $1DBC..$1DBF (input lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1AC0..$1ADF | 32 bytes | 8 mirrors of $1DDC..$1DDF (output lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1AE0..$1AFF | 32 bytes | 8 mirrors of $1DFC..$1DFF (output lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1B00..$1B7F | 128 bytes | mirror of $1D00..$1D7F | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1B80..$1B9F | 32 bytes | 8 mirrors of $1D9C..$1D9F (input lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1BA0..$1BBF | 32 bytes | 8 mirrors of $1DBC..$1DBF (input lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1BC0..$1BCF | 16 bytes | 4 mirrors of $1DDC..$1DDF (output lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1BD0..$1BDF | 16 bytes | 4 mirrors of $1DDC..$1DDF (output lines 0..3) | motherboard RAM (for storage of and use by games) | motherboard RAM? (data for/from RLG saver/calculation routines) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1BE0..$1BFF | 32 bytes | 8 mirrors of $1DFC..$1DFF (output lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1C00..$1C1F | 32 bytes | mirror of $1D00..$1D1F | unused | EPROM (RLG loader or saver routine) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1C20..$1C7F | 96 bytes | mirror of $1D20..$1D7F | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1C80..$1C9F | 32 bytes | 8 mirrors of $1D9C..$1D9F (input lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1CA0..$1CBF | 32 bytes | 8 mirrors of $1DBC..$1DBF (input lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1CC0..$1CDF | 32 bytes | 8 mirrors of $1DDC..$1DDF (output lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1CE0..$1CFF | 32 bytes | 8 mirrors of $1DFC..$1DFF (output lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1D00..$1D3F | 64 bytes | I/O #0 | $1D00..$1D0F: I/O #0: 1st PSG (Programmable Sound Generator)
$1D10..$1D1F: I/O #0: 2nd PSG (Programmable Sound Generator) $1D20: I/O #0: optional random number generator #2 ·suggested in English book, p. 161
·suggested in English magazine (Sep 1981), p. 24
·suggested in German book, p. 173
·suggested in German magazine (Sep 1981), p. 49
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1D40..$1D7F | 64 bytes | I/O #1 | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1D80..$1D9B | 28 bytes | 7 mirrors of $1D9C..$1D9F (input lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1D9C..$1D9F | 4 bytes | input lines 0..3 | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1DA0..$1DBB | 28 bytes | 7 mirrors of $1DBC..$1DBF (input lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1DBC..$1DBF | 4 bytes | input lines 4..7 (input line 7 ($1DBF) is CASIN) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1DC0..$1DDB | 28 bytes | 7 mirrors of $1DDC..$1DDF (output lines 0..3) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1DDC..$1DDF | 4 bytes | output lines 0..3 | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1DE0..$1DFB | 28 bytes | 7 mirrors of $1DFC..$1DFF (output lines 4..7) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1DFC..$1DFF | 4 bytes | output lines 4..7 (output line 7 ($1DFF) is CASOUT) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E00..$1E7F | 128 bytes | unmapped | EPROM (RLG loader or saver routine) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E80 | 1 byte | optional Interton-style noise generator | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E81..$1E87 | 7 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E88..$1E8E | 7 bytes | keypads and console | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E8F..$1E97 | 8 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E98..$1E9B | 4 bytes | mirror of $1E88..$1E8B | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1E9C..$1EA7 | 12 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EA8..$1EAE | 7 bytes | mirror of $1E88..$1E8E | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EAF..$1EB7 | 8 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EB8..$1EBB | 4 bytes | mirror of $1E88..$1E8B | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EBC..$1EC7 | 12 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EC8..$1ECE | 7 bytes | mirror of $1E88..$1E8E | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1ECF..$1ED7 | 8 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1ED8..$1EDB | 4 bytes | mirror of $1E88..$1E8B | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EDC..$1EE7 | 12 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EE8..$1EEE | 7 bytes | mirror of $1E88..$1E8E | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EEF..$1EF7 | 8 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EF8..$1EFB | 4 bytes | mirror of $1E88..$1E8B | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1EFC..$1EFF | 4 bytes | unmapped | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $1F00..$1FFF | ¼K | PVI area:
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $2000..$21FF | ½K | mirror of $0000..$01FF | unused | EPROM (RLG calculation routine) | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $2200..$3FFF | 7½K | mirror of $0200..$1FFF | EPROM (RLG games storage area) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $4000..$5FFF | 8K | mirror of $0000..$1FFF | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| $6000..$7FFF | 8K | mirror of $0000..$1FFF | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Hardware equates/memory map (basic TVGC)
Hardware equates/memory map (expanded TVGC)
"$2000..$7FFF: It is not used by any other known hardware extension, but it could be used. In fact in one of the Elektor magazines is a project from them which uses this area. It is called in the German Elektor magazine "Schnelle Spiele", meaning fast games. It was developed by Elektor for computer fairs where they presented the TVGC. They didn't want to load the games from cassette, because this would take too long for loading during the fair. So they decided to build this which loads them out of EPROMs instead from tape. It is connected to the Interton-connector of the extension board and a couple of other wires. The Interton-connector was also modified. They connected address lines A13 and A14 onto pins which they didn't use. The new board then has access to the address ranges $2000..$7FFF and $1C00..$1C7F and $1E00..$1E7F." - Manfred Schneider. For more details about the "rapid loading games" enhancement, see the relevant article in Elektor magazine.
Regarding semi-mirroring (note that this also applies to the
Interton):
"The 'I/O and control' field is actually repeated four times: $1FC0..
$1FCD, $1FD0..$1FDF, $1FE0..$1FEF, $1FF0..$1FFF. This proves of particular
interest for the data stored at addresses $1FCA and $1FCB (collisions,
VRLE, etc.). Both of these bytes are cleared when read, which can be a
nuisance. However, one reader has pointed out that reading $1FCA, say,
only clears this one byte - it does not clear $1FDA, $1FEA or $1FFA! This
means that a different address can be used for retrieving data for each
object, as required, without affecting the information required later on
for one of the other objects. Useful!" - Elektor magazine.
The NOISE generator ($1E80) is optional. The base machine generally does not have it, and the expanded machine generally does. However, many games which are nominally intended for the base machine do access this register; thus, it is included in both memory maps.
For PSG sound, the ENABLEn bits are:
Bits 7..6: unused
Bit 5 : noise C (%1=off, %0=on)
Bit 4 : noise B (%1=off, %0=on)
Bit 3 : noise A (%1=off, %0=on)
Bit 2 : tone C (%1=off, %0=on)
Bit 1 : tone B (%1=off, %0=on)
Bit 0 : tone A (%1=off, %0=on)
Eg. Tiny Tim uses the ENABLEn registers as follows:
ENABLE2:
ENABLE1:
$FF %11,111,111 no sound
$F8 %11,111,000 all noises off
all tones on
$FD %11,111,101 all noises off
tone B is on
$3B %00,111,011 while falling
tone C is on, all other channels are off
$07 %00,000,111 when you hit the ground
all noises on
all tones off
See also the "TV Games Computer" book, p. 176-184, 204-205.
The keyboard is laid out as follows (see "TV Games Computer" book, p. 31-32):
| $1E8B | $1E88 | $1E89 | $1E8A | $1E8C | $1E8D | $1E8E | Key bit |
| UC | RCAS | WCAS | C | D | E | F | bit 7 ($80) |
| START | BP1/2 | REG | 8 | 9 | A | B | bit 6 ($40) |
| LC | PC | MEM | 4 | 5 | 6 | 7 | bit 5 ($20) |
| RESET | - | + | 0 | 1 | 2 | 3 | bit 4 ($10) |
Eg. the "9" key corresponds to bit 6 of $1E8C. Bits are active high (%0=unpressed, %1=pressed). Bits 3..0 are always set.

Monitor BIOS

Monitor BIOS variables are:
| Region | Size | Label | Description | ||||||||||||||||||||||||||||
| $800..$88F | 144 bytes | MONOB | monitor object images (see diagram below):
| ||||||||||||||||||||||||||||
| $890..$897 | 8 bytes | MLINE | text line | ||||||||||||||||||||||||||||
| $898 | 1 byte | FSEQ or SILENC | function sequence indicator (BP1/2) | ||||||||||||||||||||||||||||
| $899 | 1 byte | ENTM | +, - ENTER key memory | ||||||||||||||||||||||||||||
| $89A | 1 byte | MFUNC | monitor function index | ||||||||||||||||||||||||||||
| $89B..$89C | 2 bytes | MSCR | scratch RAM for keyboard routine | ||||||||||||||||||||||||||||
| $89D | 1 byte | RKBST | right keyboard status | ||||||||||||||||||||||||||||
| $89E | 1 byte | LKBST | left keyboard status | ||||||||||||||||||||||||||||
| $89F | 1 byte | MKBST | monitor keyboard status | ||||||||||||||||||||||||||||
| $8A0..$8AB | 12 bytes | FSCRM | function scratch memory:
| ||||||||||||||||||||||||||||
| $8AC..$8B4 | 9 bytes | REGM | 2650 register status:
| ||||||||||||||||||||||||||||
| $8B5..$8B6 | 2 bytes | BK1 | breakpoint address 1 | ||||||||||||||||||||||||||||
| $8B7..$8B8 | 2 bytes | BK2 | breakpoint address 2 | ||||||||||||||||||||||||||||
| $8B9..$8BD | 5 bytes | INTADR | space for startup program | ||||||||||||||||||||||||||||
| $8BE..$8BF | 2 bytes | PC | 2650 program counter (ie. IAR) |
The BIOS character set is:
8 9 A b C d E F
G L I n P r = +
+ - : x ? _ ! N
l T i : .
Case-insensitive:
0/O 1 2/Z 3 4 5/S 6 7
$00 $01 $02 $03 $04 $05 $06 $07
--- --- --- --- --- --- --- ---
### ..# ### ### #.# ### ### ###
#.# .## ..# ..# #.# #.. #.. ..#
#.# ..# ### ### #.# ### #.. ..#
#.# ..# #.. ..# ### ..# ### ..#
#.# ..# #.. ..# ..# ..# #.# ..#
### ..# ### ### ..# ### ### ..#
$27B..$280 $281..$286 $287..$28C $28D..$292
$08 $09 $0A $0B $0C $0D $0E $0F
--- --- --- --- --- --- --- ---
### ### ### #.. ### ..# ### ###
#.# #.# #.# #.. #.. ..# #.. #..
### ### ### ### #.. ### ### ###
#.# ..# #.# #.# #.. #.# #.. #..
#.# ..# #.# #.# #.. #.# #.. #..
### ### #.# ### ### ### ### #..
$293..$298 $299..$29E $29F..$2A4 $2A5..$2AA
$10 $11 $12 $13 $14 $15 $16 $17
--- --- --- --- --- --- --- ---
### #.. ### ... ### ... ... ...
#.. #.. .#. ... #.# ... ... ...
#.. #.. .#. ### ### ### ... ...
#.. #.. .#. #.# #.. #.. ### ...
#.# #.. .#. #.# #.. #.. ... ...
### ### ### #.# #.. #.. ### ...
$2AB..$2B0 $2B1..$2B6 $2B7..$2BC $2BD..$2C2
$18 $19 $1A $1B $5F $8A $A2 $AA
--- --- --- --- --- --- --- ---
.#. ... ... ... ### ... .#. ...
.#. ... .#. #.# ..# ... .#. ###
### ### ... .#. ..# ... ... #.#
.#. ... .#. #.# ### ... .#. #.#
.#. ... ... ... #.. ... ... #.#
... ... ... ... #.. #.# ... #.#
$2C3..$2C8 $2C9..$2CE
$BB $BC $DF $E6 $F7
--- --- --- --- ---
#.. ### ..# ##. ...
#.. ### ... ##. ...
#.. .#. .## ... ...
#.. .#. ..# ... ...
#.. .#. ..# ##. ...
#.. .#. ..# ##. .#.
Present: ABCDEFG I L NOP RST X Z
Missing: H JK M Q UVW Y
Uppercase:
Present: A C EFG I L NOP ST Z
Missing: B D H JK M QR UVWXY
Lowercase:
Present: b d i l n r x
Missing: a c efgh jk m opq stuvw yz
Character imagery is stored from $27B..$580. $27B..$2CE are intentional, $2CF..$580 are unintentional. It is stored left-justified, two characters per byte (ie. one character per nybble). Each character requires 6 nybbles. Eg. "0" and "1" are stored as follows:
$27B: $E2 ###. ..#.
$27C: $A6 #.#. .##.
$27D: $A2 #.#. ..#.
$27E: $A2 #.#. ..#.
$27F: $A2 #.#. ..#.
$280: $E2 ###. ..#.
and are followed by the "2" and "3" pair at $281..$286, and so on. You can determine the ROM storage area of a character with this formula (assuming integer division; ie. round fractions down):
startaddress = $27B + ((character ÷ 2) * 6)
endaddress = $280 + ((character ÷ 2) * 6)
Therefore, for "?" ($5F = 95):
startaddress = $27B + (( 95 / 2) * 6)
= $27B + ( 47 * 6)
= $27B + 282
= $27B + $11A
= $395
and for "T" ($BC = 188):
startaddress = $27B + ((188 / 2) * 6)
= $27B + ( 94 * 6)
= $27B + 564
= $27B + $234
= $4AF
and for "5" ($05 = 5):
startaddress = $27B + (( 5 / 2) * 6)
= $27B + ( 2 * 6)
= $27B + 12
= $27B + $C
= $287
The MONOB RAM area lays out the characters on the screen as follows:
###..... $818 ###.###. $81E ###.###. $824 ###.###. $82A ]
###..... $830 ###.###. $836 ###.###. $83C ###.###. $842 ]
###..... $848 ###.###. $84E ###.###. $854 ###.###. $85A ]
###..... $860 ###.###. $866 ###.###. $86C ###.###. $872 ]
###..... $878 ###.###. $87E ###.###. $884 ###.###. $88A ]
--sprite #0-- --sprite #1-- --sprite #2-- --sprite #3--
###..... $800 ###.###. $806 ###.###. $80C ###.###. $812 ]
#.#..... $801 #.#.#... $807 ###..#.. $80D #...#... $813 ]
###.###. $802 ###.#... $808 .#...#.. $80E #...###. $814 ] original
#...#... $803 #.#.#... $809 .#...#.. $80F #...#... $815 ] sprites
#...#... $804 #.#.#... $80A .#...#.. $810 #...#... $816 ]
#...#... $805 #.#.###. $80B .#..###. $811 ###.###. $817 ]
#.#..... $819 #.#.#... $81F ###..#.. $825 #...#... $82B ]
###.###. $81A ###.#... $820 .#...#.. $826 #...###. $82C ] 1st dup.
#...#... $81B #.#.#... $821 .#...#.. $827 #...#... $82D ]
#...#... $81C #.#.#... $822 .#...#.. $828 #...#... $82E ]
#...#... $81D #.#.###. $823 .#..###. $829 ###.###. $82F ]
#.#..... $831 #.#.#... $837 ###..#.. $83D #...#... $843 ]
###.###. $832 ###.#... $838 .#...#.. $83E #...###. $844 ] 2nd dup.
#...#... $833 #.#.#... $839 .#...#.. $83F #...#... $845 ]
#...#... $834 #.#.#... $83A .#...#.. $840 #...#... $846 ]
#...#... $835 #.#.###. $83B .#..###. $841 ###.###. $847 ]
#.#..... $849 #.#.#... $84F ###..#.. $855 #...#... $85B ]
###.###. $84A ###.#... $850 .#...#.. $856 #...###. $85C ] 3rd dup.
#...#... $84B #.#.#... $851 .#...#.. $857 #...#... $85D ]
#...#... $84C #.#.#... $852 .#...#.. $858 #...#... $85E ]
#...#... $84D #.#.###. $853 .#..###. $859 ###.###. $85F ]
#.#..... $861 #.#.#... $867 ###..#.. $86D #...#... $873 ]
###.###. $862 ###.#... $868 .#...#.. $86E #...###. $874 ] 4th dup.
#...#... $863 #.#.#... $869 .#...#.. $86F #...#... $875 ]
#...#... $864 #.#.#... $86A .#...#.. $870 #...#... $876 ]
#...#... $865 #.#.###. $86B .#..###. $871 ###.###. $877 ]
#.#..... $879 #.#.#... $87F ###..#.. $885 #...#... $88B ]
###.###. $87A ###.#... $880 .#...#.. $886 #...###. $88C ] 5th dup.
#...#... $87B #.#.#... $881 .#...#.. $887 #...#... $88D ]
#...#... $87C #.#.#... $882 .#...#.. $888 #...#... $88E ]
#...#... $87D #.#.###. $883 .#..###. $889 ###.###. $88F ]
The bad monitor ROM requires mirroring of $1DBF at $19BF, as explained in the "TV Games Computer" book, p. 161.
Game startup code is:
$540:
ZPC = SADR; // $8BE..$8BF = $8A2..$8A3
SADR = BK1; // $8A2..$8A3 = $8B5..$8B6
BEGA = BK2; // $8A4..$8A5 = $8B7..$8B8
BK1 = ZBRR1; // $8B5..$8B6 = $537..$538
BK2 = ZBRR2; // $8B7..$8B8 = $539..$53A
INTADR..INTADR+4 = UMODE..UMODE+4; // $8B9..$8BD = $53B..$53F
*($8BC) = *($8B3); // PSL status
r1..r3 = *($8AD..$8AF);
r4..r6 = *($8B0..$8B2);
PSU = *($8B4);
PSL = %00000000;
goto $8BB;
$8BB:
goto $900;

Signetics EOF (Elektor Object Format)

This is the native tape format for this machine. It is is similar to the Signetics Absolute Object Format (see here) but has some differences, primarily:
block header is 'L' rather than ':';
BCC header calculation includes block header (unlike AOF);
all data is stored in binary format (AOF encodes all data except
the block header into ASCII format); and
typical payload length is 16 bytes per block rather than 30.
Each block consists of 7 bytes of header and footer, plus the actual data, as follows:
| Offset | Size | Contents | Read by |
| 0 | 1 byte | 'L' ($4C) | $797 |
| 1 | 1 byte | file number ($01..$0F) | $7A5 |
| 2..3 | 2 bytes | load address (big-endian) | $7B5 |
| 4 | 1 byte | block payload length, in bytes (usually 16) | $7BF |
| 5 | 1 byte | BCC checksum for header bytes 0..4 | $7D1 |
| 6..6+length-1 | length bytes | data payload | $7D9 |
| 6+length | 1 byte | BCC checksum for data (bytes 6..6+length-1) | $7D9 |
Checksums start as $00. For each emitted byte, the following algorithm is applied:
SUMC ^= data;
SUMC <<= 1;
Eg. for a header of $4C $0A $09 $00 $10, the checksum would be:
SUMC = 0; // SUMC is %00000000 [$00];
SUMC ^= $4C; // SUMC is %01001100 [$4C];
SUMC <<= 1; // SUMC is %10011000 [$98];
SUMC ^= $0A; // SUMC is %10010010 [$92];
SUMC <<= 1; // SUMC is %00100101 [$25];
SUMC ^= $09; // SUMC is %00101100 [$2C];
SUMC <<= 1; // SUMC is %01011000 [$58];
SUMC ^= $00; // SUMC is %01011000 [$58];
SUMC <<= 1; // SUMC is %10110000 [$B0];
SUMC ^= $10; // SUMC is %10100000 [$A0];
SUMC <<= 1; // SUMC is %01000001 [$41];
Normally, each block contains 16 actual data bytes (for a total block size
of 23 bytes). Each game finishes with a block which has 0 data bytes (and
thus no data checksum either). The address field of that block is the
starting address of the game.
Note that the Elektor BIOS seems not to bother checking the BCCs of the
last block (ie. the "start address" block). Which is just as well since
that data BCC isn't correct.
PULSE is called with the desired number of pulses in R3 (1..256). Each pulse is as follows:
CASW = $FF;
wait 8 moments (=80 µS)
CASW = $00;
wait 7 moments (=70 µS)
Each of these pulses consists of first a positive and then a negative excursion of the waveform. So it must be the case that while CASW is $FF it is writing the ascending part of the waveform and while CASW is $00 is is writing the descending part. But then CASW remains at $00 afterwards and the waveform has only silence then.
To write the PULSE TRAIN, we call PULSE(7680), then wait 500 microseconds.
To write a ONE, we call PULSE(6), then wait 500 microseconds.
To write a ZERO, we call PULSE(3), then wait 500 microseconds.
When reading, it looks for transitions where CASR is different from its previous value. There are 2 zero crossings (and 2 edges) for each pulse.
To read a bit:
r1 = CASR;
for (SILENC = 256; SILENC > 0; SILENC--)
{ r2 = 119; // transition counter
RBIT2:
for (r3 = 3; r3 > 0; r3--) // pause counter
{ NOP (ie. delay)
r0 = r1;
r1 = CASR;
r0 ^= r1;
if high bit is set (ie. there was a transition)
{ r2++;
if (r2 > 255)
{ r2 = 255;
}
// r2 will be 120..254 for the 1st..135th iterations, and 255 for the 136th and later iterations
goto RBIT2;
} }
if (r2 >= 122) // 3 or more edges
{ return r2;
} }
// timeout after 54 milliseconds
if (*($8A8) == 0) // ie. if verify mode
{ goto RBIT; // BCC error
} // implied else
goto RCAS1; // restart reading
To read a byte:
set alternate register bank, with carry, logical compare
for (MSCR = 8; MSCR > 0; MSCR--)
{ CHI2:
r5 = RBIT();
if (r5 <= 133)
{ // r5 <= 127 (ie. 8 or less edges) is an 0 bit
// r5 >= 128 && r5 <= 133 (ie. 9..14 edges) is a 1 bit
r0 = *($89C);
r5 <<= 1; // this puts the high bit of r2 into the Carry bit
r0 <<= 1; // this puts the Carry bit into the low bit of r0
*($89C) = r0;
} else
{ if (++r5 != 256)
{ goto CHI2;
} // implied else
{ goto RCAS1; // new leader (pulse train) detected
} } }
set main register bank, clear with carry
r1 = r0;
r0 ^= BCC;
r0 <<= 1;
BCC = r0;
return;
To read a file:
do
{ r2 = RBIT();
} while (r2 < 134 || r2 > 140); // wait until we read 15..21 edges
3 pulses is a clear bit (%0).
6 pulses is a set bit (%1).
9 pulses occur in inter-block gaps (sync).
Each pulse lasts 110 microseconds, so there are 9090.90' pulses per
second. Unlike with CUTS or similar formats, all pulses are the same
width, and therefore all bits are different widths, and therefore there
is no fixed data rate; it depends on the data.
Also, there are silent gaps between bits and between bytes (wheras
CUTS has no gaps), and sync pulses (not used on CUTS).
Assuming all the data was 0s, and there weren't any gaps, the baud
rate would be 3030.30' baud.
Assuming all the data was 1s, and there weren't any gaps, the baud
rate would be 1515.15' baud.
The CASIN/CASOUT registers correspond directly to what is on the
cassette; ie. the cassette interface does not encode or decode the data
but passes it directly between the computer and the cassette recorder
(unlike a typical CUTS cassette interface).
The TVC ("TVGC Cassette") file format is an emulator-only format, as follows:
| Offset | Size | Description |
| 0 | 1 byte | magic identifier byte, must be $02 |
| 1..2 | 2 bytes | loadaddress (where to start loading the program) (big-endian) |
| 3..4 | 2 bytes | loaded into $8BE.. $8BF (program start vector) (big-endian) |
| 5+ | filesize-5 | loaded into loadaddress and onwards |

Magazine Articles

Elektor magazine articles relevant to the TVGC:
| Article | ENG
| HOL
| FRA
| GER
| ITA
| SPA
| Notes |
| Elektor Software Service | JUN78 | Apr78 | SEP78 | MAY78 | - | ||
| VHF/UHF TV modulator | OCT78 | Oct78 | NOV78 | OCT78 | Dec79 | Jan81 | EPS-9967 |
| VHF/UHF TV modulator (errata) | JUN79 | Feb79 | - | - | - | - | - |
| Joysticks | NOV78 | Nov78 | - | NOV78 | Jan80 | Jul81 | - |
| Programmable Sound Generator | JAN79 | Jan79 | - | JAN79 | - | ||
| Microprocessor TV Games | APR79 | Apr79 | NOV79 | APR79 | Dec79 | Nov80 | - |
| Building the TVGC | APR79 | Apr79 | NOV79 | APR79 | Dec79 | Nov80 | - |
| Building the TVGC (errata) | JUN79 | Jun79 | - | - | - | May81 | - |
| I played TV games (Part 1) | OCT79 | Oct79 | SEP80 | OCT79 | Mar80 | Jan81 | - |
| I played TV games (Part 2) | NOV79 | Nov79 | OCT80 | DEC79 | Apr80 | Apr81 | - |
| Surround (errata) | NOV79 | Nov79 | - | DEC79 | Apr80 | - | ESS-003 |
| Elektor microprocessors | MAY80 | JUN80 | - | JUN80 | Apr81 | May80 | - |
| More on TV games: promises... | JUN80 | JAN81 | NOV80 | JUN80 | Jan81 | Dec81 | - |
| More TV games: over 20K on tape | OCT80 | - | - | OCT80 | Oct81 | ESS-007 | |
| We haven't forgotten the TVGC! | APR81 | - | - | - | - | ||
| Random number generator | JUL81 | JUL81 | JUL81 | JUL81 | Jul82 | Jul82 | - |
| TV games extended | SEP81 | SEP81 | SEP81 | SEP81 | Jan82 | Feb82 | - |
| TV games extended (errata) | OCT81 | - | Nov81 | OCT81 | - | Mar82 | - |
| Plug-in EPROM programmer | OCT81 | OCT81 | DEC81 | OCT81 | Mar82 | - | aka 2716 Programming Device |
| 15 new programs | - | - | - | OCT81 | ESS-009 | ||
| Sound effects generator | JUL82 | JUL82 | JUL82 | JUL82 | Jul83 | Jul83 | - |
| Rapid loading games | SEP82 | SEP82 | SEP82 | SEP82 | Dec82 | Jul83 | - |
| Rapid loading games (errata) | - | NOV82 | NOV82 | - | - | - | - |
| VAM: Video/Audio Modulator | FEB83 | JAN83 | - | JAN83 | Jun83 | Sep83 | - |
| VAM: Video/Audio Modulator (errata) | - | - | - | - | - | Jun84 | - |
| Universal memory card | MAR83 | MAR83 | MAR83 | MAR83 | Sep83 | Jun84 | - |
| 2650 single step | JUL83 | JUL83 | JUL83 | JUL83 | Jul84 | Jul84 | - |
| Retronics | OCT08 | OCT08 | NOV08 | OCT08 | - | ||
| Mailbox | APR09 | FEB09 | - | - | - |
Elektor magazine articles relevant only to other Signetics-based machines:
| Article | ENG
| HOL
| FRA
| GER
| ITA
| SPA
| Notes |
![]() Complex Sound Generator
| SEP78 | Sep78 | - | SEP78 | ? | ? | TI SN76477N |
ASCII Keyboard
| NOV78 | Nov78 | JAN79 | NOV78 | Jan80 | Jun81 | KB05 |
ASCII Keyboard (errata)
| DEC78 | - | - | - | - | - | - |
Elekterminal
| Dec78 | ? | ? | ? | ? | ? | - |
Capitals from the ASCII Keyboard
| MAY79 | May79 | JUN79 | SEP79 | Feb80 | ? | - |
Shift-Lock for ASCII Keyboard
| JUL79 | Jul79 | JUL79 | JUL79 | ? | ? | - |
![]() Multiple sound effects generator
| MAR81 | FEB81 | MAY81 | MAR81 | Nov81 | Oct81 | TI SN76477N. Aka Imitator |
ASCII keyboard
| MAY83 | MAY83 | MAY83 | MAY83 | Nov83 | Nov83 | - |
| Publication started | Dec74 | Apr61 | May78 | May70 | Jun79 | Jan80 | - |
| Publication ended | never | never | never | never | Apr85 | 20xx | - |
"The first Elektor in
Italian, subtitled "Electronic - Technical Science and
Pleasure", was founded by Jacopo Castelfranchi Editore (JCE) in June 1979.
In 1982 it passed to the Jackson Publishing Group. 71 issues were released
until April 1985, then Jackson renamed it Elettronica Hobby (later
becoming Fare Elettronica). In January 1987 the electronics magazine
Progetto of the JCE obtained the rights to Elektor and became, only for a
part of the pages, the Italian edition, changing its name to Progetto -
the pages of Elektor, then Progetto - Elektor and its pages, finally
Progetto Elektor. It continued until 1998, when it was replaced by
Progetto PC Upgrade. In July/August 2008 a new Italian Elektor was born,
published by Inware Edizioni, which then became digital only and ended
with the July/August 2013 issue."

Compatibility Notes
ESS-003-6: Demonstration Program: Apparently it fails to set II (Interrupt Inhibit)? (See Elektor magazine, Oct 1979, p. 31 and 37).
ESS-009-C: Circledrive: The introduction doesn't seem to work? But it seems to just be a joystick calibration routine rather than an introduction.
02-a, 02-b: These are identical except that they have different junk at $912..$917 (which is never used anyway).
03-1, 06-5: These are variants of Example2.
05-1: This is identical to Example3, except that it has different junk at $979..$9FF, $A8A..$AFF, and $BD1..$BFF (which are never used anyway) and different values in the data blocks area ($B1B..$B8B).
06-1: This is identical to 05-1, except that it has different operands in the RESET routine, and different values in the data blocks area ($B3B..$BDB).
08-1a: This is identical to Example2 except with different data ($939..$94B).
10-1a: The picture is invisible as it is drawn in blue on a blue background. To see it, you can eg. POKE BGCOLOUR $78 .
10-1b: This is identical to 08-1a except that it also contains the exploding man (jump to $9DA for unexploded version, $A1B for exploded version).
28-7 (Animated S): You must enable interrupts (POKE CPU 0 in debugger) for this to work.
Dragster: Variables are:
| Address | German
| English
|
| $1F0E | Loeschenspeicher fuer R0 von Hauptprogramm | Erasure store for R0 from main program |
| $1F0F | Joystick Daten | Joystick data |
| $1F1E | Gengenzeige (linke und rechte Haelfte) | ? (left and right half) |
| $1F1F | Flaggen (bit nr.):
7: Taste gedrueckt Flag links 6: Taste gedrueckt Flag rechts 5: Rundenzaehler Flag links 4: Rundenzaehler Flag rechts 3: Farbinvertierung 2: Stopflagge linker Spieler 1: Stopflagge recht Spieler 0: Startflagge | Flags (bit no.):
7: Key depressed flag left 6: Key depressed flag right 5: Round counter flag left 4: Round counter flag right 3: Colour inversion 2: Stop flag left player 1: Stop flag right player 0: Start flag |
| $1F4E | Hauptuhr (rechter Teil) | Main clock (right part) |
| $1F4F | Hauptuhr (linker Teil) | Main clock (left part) |
| $1F50 | Leituhr Links (rechter Teil) | Route clock left (right part) |
| $1F51 | Leituhr Links (links Teil) | Route clock left (left part) |
| $1F52 | Leituhr Rechts (rechter Teil) | Route clock right (right part) |
| $1F53 | Leituhr Rechts (links Teil) | Route clock right (left part) |
| $1F54 | Univerzalzaehler (loeschbar, ?) | Universal counter (erasable, ?) |
| $1F55 | Timingzaehler (vorwaertz) | Timing counter (before) |
| $1F56 | Offset Dragster (linke + rechte Haelfte):
0 = Dragster 1 = Stall 2 = Blown 3 = ? 4 = Gear | Offset Dragster (left + right half):
0 = Dragster 1 = Stall 2 = Blown 3 = ? 4 = Gear |
| $1F57 | Dragsterposition links | Dragster position left |
| $1F58 | Dragsterposition rechts | Dragster position right |
| $1F59 | Drehzahlmonposition links | Speed position left |
| $1F5A | Drahzahlmonposition rechts | Speed position right |
| $1F5B | Invertierungsflagge:
$00 = normal $FF = invertiert | Inversion flag:
$00 = normal $FF = inverted |
| $1F5C | Linke Haelfe: Blinkzaehler in Kombination mit $1F55 -> $D0 = 1 Minute
Rechte Haelfe: SPIELVERSIONSZAEHLER | Left half: Blink counter in combination with $1F55 - > $D0 = 1 Minute
Right half: GAME VERSION COUNTER |
| $1F5D | Offset Hinterrad (rechte + links Haelfte):
? = 0 ? = 1 weg = 2 | Back wheel offset (right + left half):
? = 0 ? = 1 off = 2 |
| $1F5E | Duplikathoehe (links + rechte Haelfte):
0 = normal 1 = schrift | Duplicate height (left + right half):
0 = normal 1 = writing |
| $1F5F | Rundenzaehler (links + rechte Halfte) | Round counter (left + right half) |
| $1F60 | Startampelfarben | Start traffic lights colours |
| $1F61 | Marker delay links | Marker delay left |
| $1F62 | Marker delay rechte | Marker delay right |
| $1F63 | Dragster ? links | Dragster ? left |
| $1F64 | Dragster ? rechts | Dragster ? right |
| $1F65 | Dragster delay (rechte und linke Haelfte) | Dragster delay (right and left halves) |
Example5 (PVI Art): Paddle movement seems to be erratic for some reason.
Explosion, Gunshot: The emulator is not currently fully compatible with these due to incomplete PSG emulation. Specifically:
sound effect should not play until START button is pressed
sound effect probably sounds quite different
sound effect should "fade out" (ie. decay)
Table 48: This will not work as-is in the emulator nor on the real machine: you need to fill in the correct data bytes first. See the book for more details.

PIPBUG/BINBUG-based Machines
Writing an output character is done from right to left (bit #0 first, then #1..#7), as follows:
Flag on
r5 = r0;
DLAY();
DLAY();
Flag off
for (r4 = 8; r4 > 0; r4--)
{ DLAY();
r5 >>= 1;
if (r5 & %10000000)
{ Flag on
} else
{ Flag off
} }
DLAY();
Flag on
CHIN returns with an input character in R0, but not until there is input
(ie. it is synchronous). The high bit is used for parity and is always
masked out by CHIN; therefore, only 7-bit input is supported. (Ie. the
extended ASCII set values $80..$FF are unsupported.)
The Sense bit is normally high. It pulses low during key transmission
(ie. whilst receiving clear bits of a byte). Waiting for the Sense bit to
become clear is therefore equivalent to "press any key to continue".
Randomization is normally done by asking the user for a keystroke, then
rapidly incrementing a register while waiting for the Sense bit to become
clear. Eg.
printf("PRESS ANY KEY");
HERE:
addi,r1 1
tpsu $80
bctr,eq HERE ;if Sense bit is set
will generate a random number (0..255) in r1.
There is also an optional 4-digit 7-segment LED display which can be
attached to the system as an additional output device. Writing to this is
done via the WRTD command. The operand is interpreted as follows:
bit 7: 1st digit
bit 6: 2nd digit
bit 5: 3rd digit
bit 4: 4th digit
bits 3..0: digit ($0..$9 = '0'..'9', $A..$F = ' ')
Eg. to write '7' to the 3rd digit would require an operand of $27. A delay is necessary between digit writes on the real machine, but not on the emulator. See the relevant magazine article for more information.
CHIN is used for cassette/papertape/keyboard. It works like this:
do
{ switch to alternate register bank
PORTC = $80; // enable tape reader
} while (Sense bit is set); // ie. until start of start bit
PORTC = 0; // disable tape reader
DLY(); // wait for half a bit (ie. until centre of start bit)
r4 = 0;
for (r5 = 8; r5 > 0; r5--)
{ DLAY(); // wait for one bit
r0 = PSU & %10000000;
r4 <<= 1;
r0 |= r4;
r4 = r0;
}
DLAY();
r4 &= %01111111; // delete parity bit
r0 = r4;
switch to main register bank
clear With Carry flag
return;
So it is expecting the following format:
.01234567#
and it returns in the middle of the stop bit (#).
So, we enable the tape reader, wait for the Sense bit to become clear,
and then disable the tape reader. Then, we read the eight bits from right
to left (bits 0..7) via direct sampling of the PSU at the appropriate
moment. The parity bit (bit 7) is then discarded (without checking it).
COUT is used for cassette/papertape/keyboard. r0 is passed as an argument; it is the ASCII character to be output. It works like this:
set Flag bit
r5 = r0;
DLAY();
DLAY();
clear Flag bit
for (r4 = 8; r4 > 0; r4--)
{ DLAY();
r5 >>= 1;
if (r5 & %10000000 == %10000000)
{ set Flag bit
} else
{ clear Flag bit
} }
DLAY();
set Flag bit
return;
So, we set the Flag bit, wait, and clear the Flag bit.
Then, we write the eight bits from left to right (bits 0..7).
The high bit is not treated any differently to the others. Then we wait
again, set the Flag bit and return.
Effectively, we write this for each byte:
##.01234567
where # means Flag set, . means Flag clear, and digits mean Flag is set/ cleared according to the relevant bit. We set the Flag before returning.
When loading, it waits until the input line goes low, then looks for the start character (':').
Some games have 110 baud and 300 baud versions. These are still all stored on cassette at 110 baud; the baud rate in this case actually refers to the speed of keyboard and screen operations, rather than cassette speed.
Various memory configurations are possible. Here are some examples, but this is not exhaustive:
| Region | Size | EA 77up2 ("Baby") | ABC/PC1500/KT9500 | EA 78up5 or PC1001 | EA 78up5 + 78up10 | Modified ABC1500 with CP1002 |
| $0000..$03FF | 1K | PIPBUG 1 monitor ROM | PIPBUG 1 monitor ROM | PIPBUG 1 monitor ROM | PIPBUG 1 monitor ROM | PIPBUG 2 monitor ROM |
| $0400..$0436 | 55 bytes | RAM for PIPBUG 1 | RAM for PIPBUG 1 | RAM for PIPBUG 1 | RAM for PIPBUG 1 | PIPLA |
| $0437..$04FF | 201 bytes | user RAM | user RAM | user RAM | user RAM | PIPLA |
| $0500..$05FF | 256 bytes | mirror of $0400..$04FF | user RAM | user RAM | user RAM | PIPLA |
| $0600..$07FF | 512 bytes | mirrors of $0400..$04FF | mirror of $0400..$05FF | user RAM | user RAM | PIPLA |
| $0800..$0861 | 98 bytes | mirror of $0000..$0061 | mirror of $0000..$0061 | user RAM on 4K version | user RAM | SMI RAM used by PIPBUG 2 + PIPLA |
| $0862..$087F | 30 bytes | mirror of $0062..$007F | mirror of $0062..$007F | user RAM on 4K version | user RAM | SMI RAM unused by PIPBUG 2 + PIPLA |
| $0880..$0BFF | 896 bytes | mirror of $0080..$03FF | mirror of $0080..$03FF | user RAM on 4K version | user RAM | unused |
| $0C00..$0DFF | 512 bytes | mirror of $0400..$05FF | mirror of $0400..$05FF | user RAM on 4K version | user RAM | motherboard RAM |
| $0E00..$0FFF | 512 bytes | mirror of $0600..$07FF | mirror of $0600..$07FF | user RAM on 4K version | user RAM | optional RAM |
| $1000..$13FF | 1K | mirror of $0000..$03FF | mirror of $0000..$03FF | user RAM on 4K version | user RAM | unmapped? |
| $1400..$1EFF | 2.75K | mirror of $0400..$0EFF | mirror of $0400..$0EFF | unused? | user RAM | unmapped? |
| $1F00..$1FFF | 256 bytes | mirror of $0F00..$0FFF | mirror of $0F00..$0FFF | unused? | user RAM | mirror of $0F00..$0FFF |
| $2000..$2FF9 | 4090 bytes | mirror of $0000..$0FF9 | mirror of $0000..$0FF9 | unused? | user RAM | unmapped? |
| $2FFA..$2FFF | 6 bytes | mirror of $0FFA..$0FFF | mirror of $0FFA..$0FFF | unused? | RAM (for use by EPROM) | unmapped? |
| $3000..$3FFF | 4K | mirror of $0000..$0FFF | mirror of $0000..$0FFF | unused? | EPROM | unmapped? |
| $4000..$41FF | 512 bytes | mirror of $0000..$01FF | mirror of $0000..$01FF | unused? | ROM? (for eg. ETI-686) | unmapped? |
| $4200..$57FF | 5.5K | mirrors of $0000..$0FFF | mirrors of $0000..$0FFF | unused? | RAM (for eg. ETI-686?) | unmapped? |
| $5800..$7CFF | 5.25K | mirrors of $0000..$0FFF | mirrors of $0000..$0FFF | unused? | RAM (for eg. ETI-686?) | unmapped? |
| $6D00..$7FFF | 4.75K | mirrors of $0000..$0FFF | mirrors of $0000..$0FFF | unused? | RAM? (eg. for Linearisatie) | unmapped? |
EA 77up2 ("Baby"): 1K ROM + 256 bytes RAM
Signetics Adaptable Board Computer aka Signetics PC1500 aka Signetics KT9500: 1K ROM + 512 bytes RAM
EA 78up5 ("1K Mini Computer" aka "2650 Mini Computer") or Signetics PC1001: 1K ROM + 1K RAM
EA 78up5+78up10 ("Expanded Mini Computer with EPROM"): 1K ROM + 15.75K RAM + 4K EPROM
Modified ABC1500 with CP1002 (see TN132): 2K ROM + 1152 bytes RAM
The ABC also supports parallel and serial I/O, has an on-board clock,
and can be expanded to up to 24K of RAM. These features are not supported
by Ami/WinPIPBUG, as the mappings of the serial and parallel I/O ports and
clock are unknown.
The Signetics PC1001 Microprocessor Prototyping Card (1K RAM)
(assembled) is a different, though closely related, machine.
The Signetics PC2000 is a 4K expansion RAM board suitable for (at least)
the PC1001/PC1500/KT9500.
The Signetics PC3000 is another "evaluation kit" (as are the other
Signetics-manufactured machines), about which almost nothing is known.
A progression of mostly Applied Technology products can be traced from
Baby 2650 to
Mini 2650 to
ETI-636 to
BINBUG-based machines to
DG680 to
Microbee.
While using PIPBUG 1 "A" and "S" commands, valid inputs are:
<CR> (ie. ENTER) to exit
<LF> (ie. Ctrl+J) to display the next address/register
<nn><CR> to change contents address/register to <nn> and exit
<nn><LF> (ie. type the value then press Ctrl+J) to change contents of address/register to
<nn> and display the next address/register.
PIPBUG 1 ROM areas are as follows:
$000..$01C: initialization
$01D..$05A: command handler
$05B..$0A3: input a cmd line into buffer
$0A4..$0AA: subr that stores double precision into temp
$0AB..$0F3: display and alter memory
$0F4..$139: selectively display and alter registers
$13A..$15F: goto address
$160..$1AA: breakpoint runtime code
$1AB..$1C9: subr to clear a bkpt
$1CA..$223: break point
$224..$23C: input two hex chars and form as byte in R1
$23D..$245: calculate the BCC char, EOR and then rotate left
$246..$24F: lookup ASCII char in hex value table
$250..$268: abort exit from any level of subr
$269..$285: byte in R1 output in hex
$286..$2A7: 110 baud input for papertape and char 1 MHz clock
$2A8..$2B3: delay for one bit time
$2B4..$2D4: COUT (Character OUT) routine
$2D5..$30F: get a number from the buffer into R1-R2
$310..$35A: dump to paper tape in object format
$35B..$3B4: subrs for outputting blanks
$3B5..$3FD: load from papertape in object format
$3FE..$3FF: unused?
Note that that PIPBUG, and programs for it, generally run with signed (arithmetic) comparisons, as opposed to the Arcadia, etc. which generally run with unsigned (logical) comparisons.
COUT has the following side effects when called:
PSL: CC = lt;
PSL: primary register bank (r1..r3) is always selected
PSU: Flag pin is always set
r0 = r4 = 0;
r5 = the old r0 (ie. what you passed)
You should not call it when SP > 5 (you need one level of stack for
COUT's return address and another level for DLAY's return address).
CHIN has the following side effects when called:
PSL: CC = gt;
PSL: primary register bank (r1..r3) is always selected
PSL: With Carry bit is always set
r0 = r4 = return code (1..127)
r5 = *(DATABUS) = 0;
You should not call it when SP > 5 (you need one level of stack for
CHIN's return address and another level for DLAY's/DLY's return
address).
Utility EPROM areas are as follows:
| Region | Label | Area | Type |
| $2FFA..$2FFB | START | RAM | data (1st CLI parameter) |
| $2FFC..$2FFD | END | RAM | data (2nd CLI parameter) |
| $2FFE..$2FFE | NEW | RAM | data (3rd CLI parameter) |
| $3C07 | GPAR | EPROM | subroutine |
| $3C2A | INCRT | EPROM | subroutine |
| $3C3C | PADR | EPROM | subroutine |
| $3C50 | HEXLIST | EPROM | subroutine |
| $3C6A | SEARCH | EPROM | subroutine |
| $3C8A | HEXIN | EPROM | subroutine |
| $3CDD | VERIFY | EPROM | subroutine |
| $3CF8 | OK | EPROM | code section |
| $3CCB | ? | EPROM | subroutine |
| $3CCE | ? | EPROM | subroutine |
| $3D0E | FAULTY | EPROM | code section |
| $3D3B | MOVE | EPROM | subroutine |
Some useful Ctrl-codes are:
Ctrl+G = BEL (7)
Ctrl+H = BS (8)
Ctrl+I = TAB (9)
Ctrl+J = LF (10)
Ctrl+M = CR (13)

Teletype I/O
At 1MHz, there are 1,000,000 short/fast cycles per second, which is 333,333.3' long/slow cycles per second. So each long/slow cycle lasts for 1,000,000÷333,333.3' = 3 µsecs.
At 110 baud, each bit ideally lasts for 9090.90' µsecs.
At 300 baud, each bit ideally lasts for 3333.3' µsecs.
At 1200 baud, each bit ideally lasts for 833.3' µsecs.
For a 110 baud teletype, a full bit delay is:
bsta,un TDLA ;3
TDLA:
eorz r0 ;2
bdrr,r0 $ ;256*3
bdrr,r0 $ ;256*3
TDLY:
bdrr,r0 $ ;256*3
lodi,r0 229 ;2
bdrr,r0 $ ;229*3
retc,un ;3
= 3001 long/slow cycles = 9003 µsecs
and a half bit delay is:
bsta,un TDLY ;3
TDLY:
bdrr,r0 $ ;256*3
lodi,r0 229 ;2
bdrr,r0 $ ;229*3
retc,un ;3
= 1463 long/slow cycles = 4389 µsecs
For a 1200 baud RS-232 terminal, a full bit delay is:
bsta,un DLAY ;3
DLAY:
lodi,r0 89 ;2
DL1:
bdrr,r0 DL1 ;3
retc,un ;3
3+2+(3*89)+3 = 275 long/slow cycles = 825 µsecs
and a half bit delay is:
bsta,un DLY ;3
DLY:
lodi,r0 58 ;2
bctr,un DL1 ;2
DL1:
bdrr,r0 DL1 ;3
retc,un ;3
3+2+2+(3*58)+3 = 184 long/slow cycle s = 552 µsecs
Note that these delays are shorter than the ideals. However, there is also code that must be run by the caller to process (emit/receive) each bit, which takes additional time to run.
Each character begins with a start bit (%0). Then data bits 0..6 are sent
(least significant bits first). Then a parity bit is sent. Then stop
bits are sent.
The letter "U" has the 7-bit ASCII code of $55 (%1010101). This would be
transmitted as %0,1010101,1,00.

Cassette I/O
A clear (0) bit (Sense bit off) is represented by a slowly pulsing signal.
About 10 slowly pulsing cycles represents a clear bit.
A set (1) bit (Sense bit on) is represented by a quickly pulsing signal.
About 20 quickly pulsing cycles represents a set bit.
The length of each bit, in time, is identical regardless of its value. (This is in contrast to the system used on the Elektor, which has identical pulses for all values and differentiates values by the positioning of the pulses.)
PIPBUG 1 encodes/decodes the files as Signetics Absolute Object Format (AOF) at 110 baud. There is a low start bit preceding each byte, and two high stop bits following each byte. The parity bit (bit 7 of the data) is always thrown away when reading. The data rate is approximately 10 raw data bytes per second. As values are encoded into ASCII pairs, the actual number of bytes loaded/saved per second from the user's point of view is about 5.
PIPBUG, BINBUG (except ACOS), CD2650 and (presumably) Selbstbaucomputer use a standard Kansas City Computer Users Tape Standard (CUTS) cassette interface to transform standard teletype I/O into cassette tape I/O (ie. high and low bits are turned into the appropriate pulse trains when recording, and pulse trains are analyzed and decoded into high and low bits during playback), usually at 110 baud:
Every "0" bit becomes 21.81' cycles (pulses) of a 2400 Hz tone, and
Every "1" bit becomes 10.90' cycles (pulses) of a 1200 Hz tone.
In practice, exactly 22 or 11 pulses should be done (as it is best to
wait until the next zero crossing before doing the next bit).
The BIOS and games only see the teletype Sense and Flag lines, they
cannot see the pulse trains. The cassette interface is invisible to the
software; as far as it knows there is only an ordinary teletype attached.
This means that you can record/play any sort of teletype I/O directly to/
from the tape, not just formal dumps.
300 baud is identical to 110 baud except that only 8 (instead of 22) or
4 (instead of 11) pulses are done; the pulses themselves are identical.
To load a tape, translate it to teletype format:
22 2400 Hz pulses in 9.09' msec = having teletype Sense low for 9.09' msec ("0").
11 1200 Hz pulses in 9.09' msec = having teletype Sense high for 9.09' msec ("1").
If we see a zero crossing every 413.2231 µsec it is a "0", and we should see 22 of those (or more if there are several 0 bits).
If we see a zero crossing every 826.4463 µsec it is a "1", and we should see 11 of those (or more if there are several 1 bits).
and vice versa when saving:
While teletype Sense is 0, flip the tape Sense every 413.2231 ÷ 2 µsec.
While teletype Sense is 1, flip the tape Sense every 826.4463 ÷ 2 µsec.
This is sufficient for all baud rates and encodings.
Here are diagrammatic views of the system, in record mode:
| At computer | Tape | Terminal (VDU/keyboard) | ||
| Flag | -> | tape can save this | -> | VDU |
| Sense | <- | input comes from kybd | <- | Keyboard |
and in playback mode:
| At computer | Tape | Terminal (VDU/keyboard) | ||
| Flag | -> | tape ignores this | -> | VDU |
| Sense | <- | input comes from tape | Neither |

Papertape I/O
The "teletype tape reader" mentioned in the Prometheus manual is a slow
one built into the teletype machine (but not the same as the printer +
keyboard). It runs at 10 characters per second, which is 110 baud
equivalent. 10 bytes = 10 characters = 1 inch = 1 second.
The "fast paper-tape reader" is a High Speed Paper Tape (HSPT) reader unit.
It run at 300 characters per second, which is 3300 baud equivalent.
For input:
If you're using a slow paper tape reader, Prometheus (and PIPBUG 1) can
control it directly via the I/O control port.
If you're using a fast paper tape reader, you need your own code (in
EPROM) at $2000..$21FF for Prometheus, and it is not supported in PIPBUG 1.
For output:
Prometheus will print a listing to the teletype as normal,
and also will punch a tape for the AOF (Signetics Absolute Object Format)
file.
Prometheus writes $C0 to the control port to read & advance the papertape.
PIPBUG 1 writes $80 in a rather tight loop (at $28A) to the I/O control
port when idle (to read from any papertape that may be present). Only
when there is no papertape in the unit can the keyboard and audio
cassette be used for input.
Writing $80 to I/O control port "enable[s paper]tape reader".
(The papertape punch must not require it, only the reader.)
So presumably when that happens the papertape reader unit reads the next
byte and then sends it one bit at a time in a teletype-like manner via
the Sense pin, and advances the papertape.
The papertape would continue to advance automatically until the motor was
turned off.
As soon as the start bit (a %0) is sent by the papertape unit and heard by
PIPBUG 1, it stops the tape reader by writing $0 to the I/O control port.
But then it reads the rest of the byte so obviously the tape reader
finishes the entire byte regardless once it has started. When it has
finished sending, it will then check again whether to send another (at
least that is how the emulator works).
When loading, PIPBUG 1 just emits $80s to the I/O control port.
When dumping, all I/O ports are idle (everything is done via the Flag
bit). The punch listens to that and when it has heard an entire byte it
punches the byte and advances the papertape (ie. it is event-driven
rather than continuous).

Printer I/O
EA printer interface:
Uses the data port for (parallel) input and output.
Does not use buffering.
Can accept a new character every 64th of a second (in condensed mode)
or every 32nd of a second (in expanded mode).
As soon as the game writes to the data port, it prints the character.
While printing is in progress, the high bit of the input data port
is low. It is high while idle.
ETI-641 printer interface:
Uses extended port $19 (25) for (parallel) input and output.
Uses an internal 128-byte buffer.
Can accept a new character every 200,000th of a second (5 µsecs).
Once the internal buffer fills, or a CR is received by the printer, it
prints (and empties) the entire buffer.
While printing is in progress, the high bit of the input extended port
$19 (25) is low. It is high while idle.
To convert from ASCII to EUY format:
output = (input & 0x1F)
| ((input & 0x60) << 1);
output = ^output;
| ASCII | EUY |
| $00..$1F | $00..$1F |
| $20..$3F | $40..$5F |
| $40..$5F | $80..$9F |
| $60..$7F | $C0..$DF |
| $80..$9F | $00..$1F |
| $A0..$BF | $40..$5F |
| $C0..$DF | $80..$9F |
| $E0..$FF | $C0..$DF |
Eg. 'A' would be $41 in ASCII format or $81 in EUY format.
The above table is before the one's complement (ie. flip all bits) operation.
Matsushita EUY-10E023LE printer model number can be decomposed as follows:
E = Electrosensitive
2 = 250mm flat cable, 372mm connector cable
3 = 32/21/16 cpl with 2 spacing dots (horizontally between each character)
L = left-to-right scanning, MSD character generator
E = manufacturer code

Unarchived Software
The following PIPBUG programs are confirmed but unavailable: C-BUG, MultiBug, MATBUG, SBCBUG, 2650 DOS, etc.
If you know of any other software, or have dumps/tapes/listings of any of the above software, please
email
us.
Various official Signetics 2650 cross-development software was available for the NCSS (National Computer Software Systems) timesharing system (running the VP/CSS OS on IBM System/370 hardware) and the GE (General Electric) Timesharing System Mark III (running the GECOS-III OS on Honeywell 645 hardware):
PIPHASM: Programmable Integrated Processor Hex Assembler
- takes ASCII source code (on disk) as input
- produces AOF file (on disk) as output
- written in FORTRAN IV
- two versions: AS1100 (16-bit) and AS1000 (32-bit).
PIPHTAP: Programmable Integrated Processor Hex Tape
- takes AOF file (on disk) as input
- punches AOF file (on paper tape) as output (for 2650 PC 1001)
- written in FORTRAN IV
PIPSTAP: Programmable Integrated Processor SMS Tape
- takes AOF file (on disk) as input
- punches SMS file (on paper tape) as output (for burning a PROM)
- written in FORTRAN IV
PIPSIM: Programmable Integrated Processor (cross-)Simulator
- takes AOF file (on disk) and ASCII command file (on disk) as input
- written in FORTRAN IV
- two versions: SM1100 (16-bit) and SM1000 (32-bit).
PLµS: Programming Language for Micro Systems
- compiler (produces AOF format as output?)
- extended version of PL/M language
- written in ? language by Gary Kildall for Signetics
- two versions: 2650PC1100 (16-bit) and 2650PL000 (32-bit).
None of this software has been dumped. The PLµS manual is sought so that this language can be reimplemented from the specification.

BINBUG Hardware
The FPGA640 + TCT PCG are mapped as follows:
| Region | Description |
| $7000..$700F | 1st..16th rows of UDG #0 imagery |
| $7010..$701F | 1st..16th rows of UDG #1 imagery |
| ... | ... |
| $77F0..$77FF | 1st..16th rows of UDG #127 imagery |
| $7800..$783F | Contents and inverse video of 1st character row (1st..64th columns):
Bit 7: inverse video (0=off, 1=on) Bits 6..0: character ($00..$7F) |
| $7840..$787F | Contents and inverse video of 2nd character row (1st..64th columns) |
| ... | ... |
| $7BC0..$7BFF | Contents and inverse video of 16th character row (1st..64th columns) |
| $7C00..$7C3F | Colours and attributes of 1st character row (1st..64th columns):
Bit 7: red (0=off, 1=on) Bit 6: green (0=off, 1=on) Bit 5: blue (0=off, 1=on) Bits 4..3: unused Bit 2: 0=PDG (Pre-Defined Graphic), 1=UDG (User-Defined Graphic) Bit 1: graphics (0=off, 1=on) Bit 0: flash (0=off, 1=on) |
| $7C40..$7C7F | Colours and attributes of 2nd character row (1st..64th columns) |
| ... | ... |
| $7FC0..$7FFF | Colours and attributes of 16th character row (1st..64th columns) |
To read the joystick buttons, you REDE from port $09. Bits are:
Bits 7..6: unused
Bits 5..3: switch bits for joystick A:
Switch '1' = %000 (fire/serve)
Switch '2' = %001
Switch '3' = %010
Switch '4' = %011
Switch '5' = %100
Switch '6' = %101
Switch '7' = %110
Nothing = %111
Bits 2..0: switch bits for joystick B (same format as for joystick A)
To read the joystick paddles, first WRTE a value of $00..$07 to port $EF, according to what you want to read:
Channel '1' (%000): 2nd joystick horizontal
Channel '2' (%001): 2nd joystick vertical
Channel '3' (%010): 1st joystick horizontal
Channel '4' (%011): 1st joystick vertical
Channel '5' (%100): 3rd joystick horizontal
Channel '6' (%101): 3rd joystick vertical
Channel '7' (%110): 4th joystick horizontal
Channel '8' (%111): 4th joystick vertical
Now REDE from port $EF in a loop until the MSB is low (ie. until something
in the $00..$7F range is returned).
The X-axis is inverted, ie. $00=right..$7F=left.
The Y-axis is normal, ie. $00=up..$7F=down.

BINBUG BIOS
The following routines are cross-compatible between PIPBUG 1 and BINBUG:
| Address | Label |
| $1D | EBUG |
| $5B | LINE |
| $8A | CRLF |
| $A4 | STRT |
| $269 | BOUT |
| $27D | AGAP |
| $286 | CHIN |
| $2B4 | COUT |
| $2DB | GNUM |
The following routines have the same names, and roughly equivalent functionality, under both PIPBUG 1 and BINBUG; however, they have different addresses and therefore are not directly cross-compatible. They may also have different register usage, stack usage, side effects, etc.:
| PIPBUG 1 | BINBUG | Label |
| $1F | $22 | MBUG |
| $AB | $B9 | ALTE |
| $F4 | $F1 | SREG |
| $131 | $121 | GOTO |
| $160 | $14A | BK01 |
| $1AB | $17B | CLBK |
| $1CA | $197 | CLR |
| $1E5 | $1A1 | BKPT |
| $246 | $28C | LKUP |
| $2A8 | $39B | DLAY |
| $2AD | $39F | DLY |
| $310 | $2E5 | DUMP |
| $35B | $27B | FORM |
| $35F | $2FB | GAP |
| $3B5 | $3C4 | LOAD |
Here is a useful table comparing various BIOSes for these machines. As there is insufficient information regarding C-BUG, SBCBUG, etc. they are not listed:
| OS | Input baud | Output baud | Tape baud | MHz | Range | Year | Notes |
PIPBUG 1
| 110 | 110 | 110 | 1 | $0..$3FF | ? | EA 300 baud mod is possible |
PIPBUG 2
| 110/300 | 110/300 | 110/300? | 1 | $0..$3FF | ? | Supports both rates |
HYBUG
| 300 | 300 | High-speed | 1 | ? | ? | 600 and 1200 baud mods are possible |
BINBUG 3.5
| 300/parallel? | DG640 | 300 | 1? | $0..$7FF | ? | - |
BINBUG 3.6
| 300/parallel? | DG640 | 300 | 1 | $0..$7FF | 1979 | BINBUG3.6.pdf |
BINBUG 4.4
| 300 | DG640 | ACOS | 1? | $0..$7FF | ? | Supports ACOS and DOS |
BINBUG 4.5
| ? | DG640 | ACOS | 1? | $0..$7FF | ? | Supports ACOS and DOS |
BINBUG 5.2
| 1200 | 1200 | ACOS | 1? | $0..$7FF | ? | Supports ACOS and DOS |
BINBUG 5.3
| ? | serial | ACOS | ? | $0..$7FF | ? | - |
BINBUG 6.0
| Eurocard | Eurocard | ACOS | ? | $0..$7FF | ? | - |
BINBUG 6.1
| 150?/300/1200/2400/parallel | DG640 | ACOS | ? | $0..$7FF | 1982 | sbcos_manual.pdf . Supports ACOS and VHSDOS |
BINBUG 7.1
| 300/1200/2400/parallel | 300/1200/2400 | ACOS | ? | $0..$7FF | 1982 | sbcos_manual.pdf . Supports ACOS and VHSDOS |
GBUG
| 300 | DG640 | ? | 1/2 | $0..$7FF | ? | Optional parallel keyboard support |
MATBUG 4.1
| Eurocard | DG640 | ? | ? | $0..$7FF | ? | matbug_monitor_for_eurocard_system_notes.pdf |
MIKEBUG 3
| 300 | DG640 | ? | 1? | $0..$7FF | ? | - |
Multibug (serial version)
| 300 | 300 | 300 | ? | $0..$7FF | 1981 | ETI-685 |
Multibug (memory-mapped version)
| parallel | DG640 | 300 | ? | $0..$7FF | 1981 | ETI-685 |
MYBUG
| 300 | DG640 | ? | 1? | $0..$7FF | ? | - |
ACOS 2.C
| - | - | Control & data I/O ports | 1? | $6000..$63FF | ? | - |
ACOS 3.C
| - | - | Extended I/O ports? | 1? | $6000..$63FF | ? | - |
ACOS 3.E
| - | - | Extended I/O ports | 1 | $6000..$63FF | 1982 | sbcos_manual.pdf |
VHSDOS 2.6a
| - | - | - | 1? | $6800..$6FFF | 1981 | vhs_dos_v26a_source_listing.pdf |
MicroDOS 4.5a
| - | - | - | 1? | $6800..$6FFF | ? | MICRODOS.SRC |
Baud rates given assume 1 MHz operation (and are therefore doubled at 2 MHz).
BINBUG outputs both to the serial port (at 300 baud) and to the VDU (1K RAM at $7800..$7FFF).
According to ETI Oct 1982, BINBUG can work at 300, 1200 & 2400 baud (!).
SBCOS = SBCBUG = BINBUG 6.1 + BINBUG 7.1 + ACOS 3.E
BINBUG 6.1 & 7.1 support/expect ETI-685 processor board.

Floppy Disk I/O
Each block is 256 bytes, as follows:
0: next track (0..39).
1: next sector (1..10).
2..255: data bytes
CMD files are used by VHSDOS and MicroDOS for storage of games. They normally consist of two or more chunks concatenated together. Each chunk has a 3-byte header:
0..1: load address of chunk (big-endian)
2: length of payload in bytes (normally <= $FB)
then the payload itself (if any) follows.
The CMD file is terminated by a chunk like this:
0..1: start address of game (big-endian)
2: $00
with no payload.
CMD chunks can seamlessly cross block boundaries.
Note that the above assumes that the block header (ie. "next track" and
"next sector" bytes) have already been skipped.
The 10 sectors per track are numbered 1..10 and have an interleave of 7, ie.
1, 8, 5, 2, 9, 6, 3, 10, 7, 4. (The available disk images are already deinterleaved.)
At the flux level, there are 250,000 flux transitions per second.
Each bit is 1 clock flux + 1 data flux, so there are 125,000 bits per sec.
So theoretically 15,625 bytes per sec, if there were no sector headers,
inter-sector gaps, etc.
However, post-read processing must occur, so we can only really achieve
1/8th of that speed (hence the interleaving). Thus, an effective speed of
12,800 bytes ÷ 8 = 1,600 bytes per second.
After each 20 msec sector read, there is about 140 msec of post-processing
as the disk continues to spin. But the CPU has to keep up with the
drive as it reads each byte, because the drive has no buffer. Therefore most
of the time the CPU is not bothering to read the data passing under the head,
but is instead post-processing previously read data.
With an infinitely fast disk, it takes about 30,642 clocks. ie. about
30.642 msec, between reading an arbitrary byte in a given sector and
reading the equivalent byte in the next sector.
It also takes additional time to change tracks, and to start or stop the
motor.

Game Help
These do nothing very useful, but are not expected to (eg. they are for controlling unemulated hardware, or are code fragments for incorporation into your own games):
2708 EPROM Programmer
Linearization (Linearisatie)
Vector Magnetometer
Wind Furnace Controller
most routines
These games are hardcoded for 110 baud:
On-screen Clock
PPI-based EPROM Programmer
110 baud version of Lunar Lander (machine code)
110 baud version of Biorhythms
110 baud version of Funny Farm Races
These games are hardcoded for 300 baud:
Astro Trek (but an official 110 baud patch is provided with the listing)
Reaction Timer
300 baud version of Lunar Lander (machine code)
300 baud version of Biorhythms
300 baud version of Funny Farm Races
2650 Line Assembler:
"It is not identical but is very similar to the Line Assembler described in the article "2650 mini assembler simplifies programming" by Jamieson Rowe published in the April 1979 issue of Electronics Australia (p. 76-80) and the follow-up article "Improving the 2650 mini line assembler" by A. M. Kollosche in February 1980 (p. 76)." - Chris Burrows.
The start address begin at 2, and increments by 2 every time F5 (reset) is pressed, for some reason.
2650 Micro BASIC programs (eg.
Acey-Deucy,
Blackjack,
Guessing Game (2650 Micro BASIC version),
Life (2650 Micro BASIC version),
Lunar Lander (2650 Micro BASIC version),
Number Game,
Radio Log,
Temperature Conversion):
Type G1 and then press ENTER to begin execution.
Type L1 and then press ENTER to list the program.
Type E1 and then press ENTER to replace lines starting from 1.
Ctrl-C when done.
Some program statements are:
| Letter | Description | Example | Standard BASIC |
| A | ASCII input | AD | INPUT D$:LET D=ASC(LEFT$(D$,1)) |
| E | End | E | END |
| G | GoTo | G5 | GOTO 5 |
| I | Numeric input | ID | INPUT D |
| L | Let | L0=D | LET D=0 |
| P | P"HELLO" | PRINT "HELLO" | |
| T | Test (if) | TD>0 | IF D>0 THEN |
| $ | Remark | $HELLO$ | REM HELLO |
Reverse Polish Notation is used. Eg. LVD+#=D,FT-=F means:
L Let
V push V onto the stack
D push D onto the stack
+ add them together
# unary negation of the result (ie. result = -result)
= store the result in
D variable D
, Let again
F push F onto the stack
T push T onto the stack
- subtract T from F
= store the result in
F variable F
Alien Hunt:
Has ! and " at end of table rows, for some reason.
Assembler, AssemblerPlusDemonstration, AssemblerPlusAssemblerList:
AssemblerPlusDemonstration.pgm will assemble without errors, but the generated machine code is not being written to memory anywhere (we are asking in this case for ORG $2000, but it doesn't seem to matter where we ask for, it is never generated anywhere). Hence, the current dump of Assembler.pgm should be considered suspect (although it has been verified). As the other two are based on that dump, they are likewise suspect.
Astro Trek:
Here is a map of all 2401 (7*7*7*7) sectors of the galaxy:
Quadrant 1
Quadrant 2
Quadrant 3
Quadrant 4
Quadrant 5
Quadrant 6
Quadrant 7
S1
S2
S3
S4
S5
S6
S7
S1
S2
S3
S4
S5
S6
S7
S1
S2
S3
S4
S5
S6
S7
S1
S2
S3
S4
S5
S6
S7
S1
S2
S3
S4
S5
S6
S7
S1
S2
S3
S4
S5
S6
S7
S1
S2
S3
S4
S5
S6
S7
Q1
S1
1,1
1,1
1,1
2,1
1,1
3,1
1,1
4,1
1,1
5,1
1,1
6,1
1,1
7,1
2,1
1,1
2,1
2,1
2,1
3,1
2,1
4,1
2,1
5,1
2,1
6,1
2,1
7,1
3,1
1,1
3,1
2,1
3,1
3,1
3,1
4,1
3,1
5,1
3,1
6,1
3,1
7,1
4,1
1,1
4,1
2,1
4,1
3,1
4,1
4,1
4,1
5,1
4,1
6,1
4,1
7,1
5,1
1,1
5,1
2,1
5,1
3,1
5,1
4,1
5,1
5,1
5,1
6,1
5,1
7,1
6,1
1,1
6,1
2,1
6,1
3,1
6,1
4,1
6,1
5,1
6,1
6,1
6,1
7,1
7,1
1,1
7,1
2,1
7,1
3,1
7,1
4,1
7,1
5,1
7,1
6,1
7,1
7,1
S2
1,1
1,2
1,1
2,2
1,1
3,2
1,1
4,2
1,1
5,2
1,1
6,2
1,1
7,2
2,1
1,2
2,1
2,2
2,1
3,2
2,1
4,2
2,1
5,2
2,1
6,2
2,1
7,2
3,1
1,2
3,1
2,2
3,1
3,2
3,1
4,2
3,1
5,2
3,1
6,2
3,1
7,2
4,1
1,2
4,1
2,2
4,1
3,2
4,1
4,2
4,1
5,2
4,1
6,2
4,1
7,2
5,1
1,2
5,1
2,2
5,1
3,2
5,1
4,2
5,1
5,2
5,1
6,2
5,1
7,2
6,1
1,2
6,1
2,2
6,1
3,2
6,1
4,2
6,1
5,2
6,1
6,2
6,1
7,2
7,1
1,2
7,1
2,2
7,1
3,2
7,1
4,2
7,1
5,2
7,1
6,2
7,1
7,2
S3
1,1
1,3
1,1
2,3
1,1
3,3
1,1
4,3
1,1
5,3
1,1
6,3
1,1
7,3
2,1
1,3
2,1
2,3
2,1
3,3
2,1
4,3
2,1
5,3
2,1
6,3
2,1
7,3
3,1
1,3
3,1
2,3
3,1
3,3
3,1
4,3
3,1
5,3
3,1
6,3
3,1
7,3
4,1
1,3
4,1
2,3
4,1
3,3
4,1
4,3
4,1
5,3
4,1
6,3
4,1
7,3
5,1
1,3
5,1
2,3
5,1
3,3
5,1
4,3
5,1
5,3
5,1
6,3
5,1
7,3
6,1
1,3
6,1
2,3
6,1
3,3
6,1
4,3
6,1
5,3
6,1
6,3
6,1
7,3
7,1
1,3
7,1
2,3
7,1
3,3
7,1
4,3
7,1
5,3
7,1
6,3
7,1
7,3
S4
1,1
1,4
1,1
2,4
1,1
3,4
1,1
4,4
1,1
5,4
1,1
6,4
1,1
7,4
2,1
1,4
2,1
2,4
2,1
3,4
2,1
4,4
2,1
5,4
2,1
6,4
2,1
7,4
3,1
1,4
3,1
2,4
3,1
3,4
3,1
4,4
3,1
5,4
3,1
6,4
3,1
7,4
4,1
1,4
4,1
2,4
4,1
3,4
4,1
4,4
4,1
5,4
4,1
6,4
4,1
7,4
5,1
1,4
5,1
2,4
5,1
3,4
5,1
4,4
5,1
5,4
5,1
6,4
5,1
7,4
6,1
1,4
6,1
2,4
6,1
3,4
6,1
4,4
6,1
5,4
6,1
6,4
6,1
7,4
7,1
1,4
7,1
2,4
7,1
3,4
7,1
4,4
7,1
5,4
7,1
6,4
7,1
7,4
S5
1,1
1,5
1,1
2,5
1,1
3,5
1,1
4,5
1,1
5,5
1,1
6,5
1,1
7,5
2,1
1,5
2,1
2,5
2,1
3,5
2,1
4,5
2,1
5,5
2,1
6,5
2,1
7,5
3,1
1,5
3,1
2,5
3,1
3,5
3,1
4,5
3,1
5,5
3,1
6,5
3,1
7,5
4,1
1,5
4,1
2,5
4,1
3,5
4,1
4,5
4,1
5,5
4,1
6,5
4,1
7,5
5,1
1,5
5,1
2,5
5,1
3,5
5,1
4,5
5,1
5,5
5,1
6,5
5,1
7,5
6,1
1,5
6,1
2,5
6,1
3,5
6,1
4,5
6,1
5,5
6,1
6,5
6,1
7,5
7,1
1,5
7,1
2,5
7,1
3,5
7,1
4,5
7,1
5,5
7,1
6,5
7,1
7,5
S6
1,1
1,6
1,1
2,6
1,1
3,6
1,1
4,6
1,1
5,6
1,1
6,6
1,1
7,6
2,1
1,6
2,1
2,6
2,1
3,6
2,1
4,6
2,1
5,6
2,1
6,6
2,1
7,6
3,1
1,6
3,1
2,6
3,1
3,6
3,1
4,6
3,1
5,6
3,1
6,6
3,1
7,6
4,1
1,6
4,1
2,6
4,1
3,6
4,1
4,6
4,1
5,6
4,1
6,6
4,1
7,6
5,1
1,6
5,1
2,6
5,1
3,6
5,1
4,6
5,1
5,6
5,1
6,6
5,1
7,6
6,1
1,6
6,1
2,6
6,1
3,6
6,1
4,6
6,1
5,6
6,1
6,6
6,1
7,6
7,1
1,6
7,1
2,6
7,1
3,6
7,1
4,6
7,1
5,6
7,1
6,6
7,1
7,6
S7
1,1
1,7
1,1
2,7
1,1
3,7
1,1
4,7
1,1
5,7
1,1
6,7
1,1
7,7
2,1
1,7
2,1
2,7
2,1
3,7
2,1
4,7
2,1
5,7
2,1
6,7
2,1
7,7
3,1
1,7
3,1
2,7
3,1
3,7
3,1
4,7
3,1
5,7
3,1
6,7
3,1
7,7
4,1
1,7
4,1
2,7
4,1
3,7
4,1
4,7
4,1
5,7
4,1
6,7
4,1
7,7
5,1
1,7
5,1
2,7
5,1
3,7
5,1
4,7
5,1
5,7
5,1
6,7
5,1
7,7
6,1
1,7
6,1
2,7
6,1
3,7
6,1
4,7
6,1
5,7
6,1
6,7
6,1
7,7
7,1
1,7
7,1
2,7
7,1
3,7
7,1
4,7
7,1
5,7
7,1
6,7
7,1
7,7
Q2
S1
1,2
1,1
1,2
2,1
1,2
3,1
1,2
4,1
1,2
5,1
1,2
6,1
1,2
7,1
2,2
1,1
2,2
2,1
2,2
3,1
2,2
4,1
2,2
5,1
2,2
6,1
2,2
7,1
3,2
1,1
3,2
2,1
3,2
3,1
3,2
4,1
3,2
5,1
3,2
6,1
3,2
7,1
4,2
1,1
4,2
2,1
4,2
3,1
4,2
4,1
4,2
5,1
4,2
6,1
4,2
7,1
5,2
1,1
5,2
2,1
5,2
3,1
5,2
4,1
5,2
5,1
5,2
6,1
5,2
7,1
6,2
1,1
6,2
2,1
6,2
3,1
6,2
4,1
6,2
5,1
6,2
6,1
6,2
7,1
7,2
1,1
7,2
2,1
7,2
3,1
7,2
4,1
7,2
5,1
7,2
6,1
7,2
7,1
S2
1,2
1,2
1,2
2,2
1,2
3,2
1,2
4,2
1,2
5,2
1,2
6,2
1,2
7,2
2,2
1,2
2,2
2,2
2,2
3,2
2,2
4,2
2,2
5,2
2,2
6,2
2,2
7,2
3,2
1,2
3,2
2,2
3,2
3,2
3,2
4,2
3,2
5,2
3,2
6,2
3,2
7,2
4,2
1,2
4,2
2,2
4,2
3,2
4,2
4,2
4,2
5,2
4,2
6,2
4,2
7,2
5,2
1,2
5,2
2,2
5,2
3,2
5,2
4,2
5,2
5,2
5,2
6,2
5,2
7,2
6,2
1,2
6,2
2,2
6,2
3,2
6,2
4,2
6,2
5,2
6,2
6,2
6,2
7,2
7,2
1,2
7,2
2,2
7,2
3,2
7,2
4,2
7,2
5,2
7,2
6,2
7,2
7,2
S3
1,2
1,3
1,2
2,3
1,2
3,3
1,2
4,3
1,2
5,3
1,2
6,3
1,2
7,3
2,2
1,3
2,2
2,3
2,2
3,3
2,2
4,3
2,2
5,3
2,2
6,3
2,2
7,3
3,2
1,3
3,2
2,3
3,2
3,3
3,2
4,3
3,2
5,3
3,2
6,3
3,2
7,3
4,2
1,3
4,2
2,3
4,2
3,3
4,2
4,3
4,2
5,3
4,2
6,3
4,2
7,3
5,2
1,3
5,2
2,3
5,2
3,3
5,2
4,3
5,2
5,3
5,2
6,3
5,2
7,3
6,2
1,3
6,2
2,3
6,2
3,3
6,2
4,3
6,2
5,3
6,2
6,3
6,2
7,3
7,2
1,3
7,2
2,3
7,2
3,3
7,2
4,3
7,2
5,3
7,2
6,3
7,2
7,3
S4
1,2
1,4
1,2
2,4
1,2
3,4
1,2
4,4
1,2
5,4
1,2
6,4
1,2
7,4
2,2
1,4
2,2
2,4
2,2
3,4
2,2
4,4
2,2
5,4
2,2
6,4
2,2
7,4
3,2
1,4
3,2
2,4
3,2
3,4
3,2
4,4
3,2
5,4
3,2
6,4
3,2
7,4
4,2
1,4
4,2
2,4
4,2
3,4
4,2
4,4
4,2
5,4
4,2
6,4
4,2
7,4
5,2
1,4
5,2
2,4
5,2
3,4
5,2
4,4
5,2
5,4
5,2
6,4
5,2
7,4
6,2
1,4
6,2
2,4
6,2
3,4
6,2
4,4
6,2
5,4
6,2
6,4
6,2
7,4
7,2
1,4
7,2
2,4
7,2
3,4
7,2
4,4
7,2
5,4
7,2
6,4
7,2
7,4
S5
1,2
1,5
1,2
2,5
1,2
3,5
1,2
4,5
1,2
5,5
1,2
6,5
1,2
7,5
2,2
1,5
2,2
2,5
2,2
3,5
2,2
4,5
2,2
5,5
2,2
6,5
2,2
7,5
3,2
1,5
3,2
2,5
3,2
3,5
3,2
4,5
3,2
5,5
3,2
6,5
3,2
7,5
4,2
1,5
4,2
2,5
4,2
3,5
4,2
4,5
4,2
5,5
4,2
6,5
4,2
7,5
5,2
1,5
5,2
2,5
5,2
3,5
5,2
4,5
5,2
5,5
5,2
6,5
5,2
7,5
6,2
1,5
6,2
2,5
6,2
3,5
6,2
4,5
6,2
5,5
6,2
6,5
6,2
7,5
7,2
1,5
7,2
2,5
7,2
3,5
7,2
4,5
7,2
5,5
7,2
6,5
7,2
7,5
S6
1,2
1,6
1,2
2,6
1,2
3,6
1,2
4,6
1,2
5,6
1,2
6,6
1,2
7,6
2,2
1,6
2,2
2,6
2,2
3,6
2,2
4,6
2,2
5,6
2,2
6,6
2,2
7,6
3,2
1,6
3,2
2,6
3,2
3,6
3,2
4,6
3,2
5,6
3,2
6,6
3,2
7,6
4,2
1,6
4,2
2,6
4,2
3,6
4,2
4,6
4,2
5,6
4,2
6,6
4,2
7,6
5,2
1,6
5,2
2,6
5,2
3,6
5,2
4,6
5,2
5,6
5,2
6,6
5,2
7,6
6,2
1,6
6,2
2,6
6,2
3,6
6,2
4,6
6,2
5,6
6,2
6,6
6,2
7,6
7,2
1,6
7,2
2,6
7,2
3,6
7,2
4,6
7,2
5,6
7,2
6,6
7,2
7,6
S7
1,2
1,7
1,2
2,7
1,2
3,7
1,2
4,7
1,2
5,7
1,2
6,7
1,2
7,7
2,2
1,7
2,2
2,7
2,2
3,7
2,2
4,7
2,2
5,7
2,2
6,7
2,2
7,7
3,2
1,7
3,2
2,7
3,2
3,7
3,2
4,7
3,2
5,7
3,2
6,7
3,2
7,7
4,2
1,7
4,2
2,7
4,2
3,7
4,2
4,7
4,2
5,7
4,2
6,7
4,2
7,7
5,2
1,7
5,2
2,7
5,2
3,7
5,2
4,7
5,2
5,7
5,2
6,7
5,2
7,7
6,2
1,7
6,2
2,7
6,2
3,7
6,2
4,7
6,2
5,7
6,2
6,7
6,2
7,7
7,2
1,7
7,2
2,7
7,2
3,7
7,2
4,7
7,2
5,7
7,2
6,7
7,2
7,7
Q3
S1
1,3
1,1
1,3
2,1
1,3
3,1
1,3
4,1
1,3
5,1
1,3
6,1
1,3
7,1
2,3
1,1
2,3
2,1
2,3
3,1
2,3
4,1
2,3
5,1
2,3
6,1
2,3
7,1
3,3
1,1
3,3
2,1
3,3
3,1
3,3
4,1
3,3
5,1
3,3
6,1
3,3
7,1
4,3
1,1
4,3
2,1
4,3
3,1
4,3
4,1
4,3
5,1
4,3
6,1
4,3
7,1
5,3
1,1
5,3
2,1
5,3
3,1
5,3
4,1
5,3
5,1
5,3
6,1
5,3
7,1
6,3
1,1
6,3
2,1
6,3
3,1
6,3
4,1
6,3
5,1
6,3
6,1
6,3
7,1
7,3
1,1
7,3
2,1
7,3
3,1
7,3
4,1
7,3
5,1
7,3
6,1
7,3
7,1
S2
1,3
1,2
1,3
2,2
1,3
3,2
1,3
4,2
1,3
5,2
1,3
6,2
1,3
7,2
2,3
1,2
2,3
2,2
2,3
3,2
2,3
4,2
2,3
5,2
2,3
6,2
2,3
7,2
3,3
1,2
3,3
2,2
3,3
3,2
3,3
4,2
3,3
5,2
3,3
6,2
3,3
7,2
4,3
1,2
4,3
2,2
4,3
3,2
4,3
4,2
4,3
5,2
4,3
6,2
4,3
7,2
5,3
1,2
5,3
2,2
5,3
3,2
5,3
4,2
5,3
5,2
5,3
6,2
5,3
7,2
6,3
1,2
6,3
2,2
6,3
3,2
6,3
4,2
6,3
5,2
6,3
6,2
6,3
7,2
7,3
1,2
7,3
2,2
7,3
3,2
7,3
4,2
7,3
5,2
7,3
6,2
7,3
7,2
S3
1,3
1,3
1,3
2,3
1,3
3,3
1,3
4,3
1,3
5,3
1,3
6,3
1,3
7,3
2,3
1,3
2,3
2,3
2,3
3,3
2,3
4,3
2,3
5,3
2,3
6,3
2,3
7,3
3,3
1,3
3,3
2,3
3,3
3,3
3,3
4,3
3,3
5,3
3,3
6,3
3,3
7,3
4,3
1,3
4,3
2,3
4,3
3,3
4,3
4,3
4,3
5,3
4,3
6,3
4,3
7,3
5,3
1,3
5,3
2,3
5,3
3,3
5,3
4,3
5,3
5,3
5,3
6,3
5,3
7,3
6,3
1,3
6,3
2,3
6,3
3,3
6,3
4,3
6,3
5,3
6,3
6,3
6,3
7,3
7,3
1,3
7,3
2,3
7,3
3,3
7,3
4,3
7,3
5,3
7,3
6,3
7,3
7,3
S4
1,3
1,4
1,3
2,4
1,3
3,4
1,3
4,4
1,3
5,4
1,3
6,4
1,3
7,4
2,3
1,4
2,3
2,4
2,3
3,4
2,3
4,4
2,3
5,4
2,3
6,4
2,3
7,4
3,3
1,4
3,3
2,4
3,3
3,4
3,3
4,4
3,3
5,4
3,3
6,4
3,3
7,4
4,3
1,4
4,3
2,4
4,3
3,4
4,3
4,4
4,3
5,4
4,3
6,4
4,3
7,4
5,3
1,4
5,3
2,4
5,3
3,4
5,3
4,4
5,3
5,4
5,3
6,4
5,3
7,4
6,3
1,4
6,3
2,4
6,3
3,4
6,3
4,4
6,3
5,4
6,3
6,4
6,3
7,4
7,3
1,4
7,3
2,4
7,3
3,4
7,3
4,4
7,3
5,4
7,3
6,4
7,3
7,4
S5
1,3
1,5
1,3
2,5
1,3
3,5
1,3
4,5
1,3
5,5
1,3
6,5
1,3
7,5
2,3
1,5
2,3
2,5
2,3
3,5
2,3
4,5
2,3
5,5
2,3
6,5
2,3
7,5
3,3
1,5
3,3
2,5
3,3
3,5
3,3
4,5
3,3
5,5
3,3
6,5
3,3
7,5
4,3
1,5
4,3
2,5
4,3
3,5
4,3
4,5
4,3
5,5
4,3
6,5
4,3
7,5
5,3
1,5
5,3
2,5
5,3
3,5
5,3
4,5
5,3
5,5
5,3
6,5
5,3
7,5
6,3
1,5
6,3
2,5
6,3
3,5
6,3
4,5
6,3
5,5
6,3
6,5
6,3
7,5
7,3
1,5
7,3
2,5
7,3
3,5
7,3
4,5
7,3
5,5
7,3
6,5
7,3
7,5
S6
1,3
1,6
1,3
2,6
1,3
3,6
1,3
4,6
1,3
5,6
1,3
6,6
1,3
7,6
2,3
1,6
2,3
2,6
2,3
3,6
2,3
4,6
2,3
5,6
2,3
6,6
2,3
7,6
3,3
1,6
3,3
2,6
3,3
3,6
3,3
4,6
3,3
5,6
3,3
6,6
3,3
7,6
4,3
1,6
4,3
2,6
4,3
3,6
4,3
4,6
4,3
5,6
4,3
6,6
4,3
7,6
5,3
1,6
5,3
2,6
5,3
3,6
5,3
4,6
5,3
5,6
5,3
6,6
5,3
7,6
6,3
1,6
6,3
2,6
6,3
3,6
6,3
4,6
6,3
5,6
6,3
6,6
6,3
7,6
7,3
1,6
7,3
2,6
7,3
3,6
7,3
4,6
7,3
5,6
7,3
6,6
7,3
7,6
S7
1,3
1,7
1,3
2,7
1,3
3,7
1,3
4,7
1,3
5,7
1,3
6,7
1,3
7,7
2,3
1,7
2,3
2,7
2,3
3,7
2,3
4,7
2,3
5,7
2,3
6,7
2,3
7,7
3,3
1,7
3,3
2,7
3,3
3,7
3,3
4,7
3,3
5,7
3,3
6,7
3,3
7,7
4,3
1,7
4,3
2,7
4,3
3,7
4,3
4,7
4,3
5,7
4,3
6,7
4,3
7,7
5,3
1,7
5,3
2,7
5,3
3,7
5,3
4,7
5,3
5,7
5,3
6,7
5,3
7,7
6,3
1,7
6,3
2,7
6,3
3,7
6,3
4,7
6,3
5,7
6,3
6,7
6,3
7,7
7,3
1,7
7,3
2,7
7,3
3,7
7,3
4,7
7,3
5,7
7,3
6,7
7,3
7,7
Q4
S1
1,4
1,1
1,4
2,1
1,4
3,1
1,4
4,1
1,4
5,1
1,4
6,1
1,4
7,1
2,4
1,1
2,4
2,1
2,4
3,1
2,4
4,1
2,4
5,1
2,4
6,1
2,4
7,1
3,4
1,1
3,4
2,1
3,4
3,1
3,4
4,1
3,4
5,1
3,4
6,1
3,4
7,1
4,4
1,1
4,4
2,1
4,4
3,1
4,4
4,1
4,4
5,1
4,4
6,1
4,4
7,1
5,4
1,1
5,4
2,1
5,4
3,1
5,4
4,1
5,4
5,1
5,4
6,1
5,4
7,1
6,4
1,1
6,4
2,1
6,4
3,1
6,4
4,1
6,4
5,1
6,4
6,1
6,4
7,1
7,4
1,1
7,4
2,1
7,4
3,1
7,4
4,1
7,4
5,1
7,4
6,1
7,4
7,1
S2
1,4
1,2
1,4
2,2
1,4
3,2
1,4
4,2
1,4
5,2
1,4
6,2
1,4
7,2
2,4
1,2
2,4
2,2
2,4
3,2
2,4
4,2
2,4
5,2
2,4
6,2
2,4
7,2
3,4
1,2
3,4
2,2
3,4
3,2
3,4
4,2
3,4
5,2
3,4
6,2
3,4
7,2
4,4
1,2
4,4
2,2
4,4
3,2
4,4
4,2
4,4
5,2
4,4
6,2
4,4
7,2
5,4
1,2
5,4
2,2
5,4
3,2
5,4
4,2
5,4
5,2
5,4
6,2
5,4
7,2
6,4
1,2
6,4
2,2
6,4
3,2
6,4
4,2
6,4
5,2
6,4
6,2
6,4
7,2
7,4
1,2
7,4
2,2
7,4
3,2
7,4
4,2
7,4
5,2
7,4
6,2
7,4
7,2
S3
1,4
1,3
1,4
2,3
1,4
3,3
1,4
4,3
1,4
5,3
1,4
6,3
1,4
7,3
2,4
1,3
2,4
2,3
2,4
3,3
2,4
4,3
2,4
5,3
2,4
6,3
2,4
7,3
3,4
1,3
3,4
2,3
3,4
3,3
3,4
4,3
3,4
5,3
3,4
6,3
3,4
7,3
4,4
1,3
4,4
2,3
4,4
3,3
4,4
4,3
4,4
5,3
4,4
6,3
4,4
7,3
5,4
1,3
5,4
2,3
5,4
3,3
5,4
4,3
5,4
5,3
5,4
6,3
5,4
7,3
6,4
1,3
6,4
2,3
6,4
3,3
6,4
4,3
6,4
5,3
6,4
6,3
6,4
7,3
7,4
1,3
7,4
2,3
7,4
3,3
7,4
4,3
7,4
5,3
7,4
6,3
7,4
7,3
S4
1,4
1,4
1,4
2,4
1,4
3,4
1,4
4,4
1,4
5,4
1,4
6,4
1,4
7,4
2,4
1,4
2,4
2,4
2,4
3,4
2,4
4,4
2,4
5,4
2,4
6,4
2,4
7,4
3,4
1,4
3,4
2,4
3,4
3,4
3,4
4,4
3,4
5,4
3,4
6,4
3,4
7,4
4,4
1,4
4,4
2,4
4,4
3,4
4,4
4,4
4,4
5,4
4,4
6,4
4,4
7,4
5,4
1,4
5,4
2,4
5,4
3,4
5,4
4,4
5,4
5,4
5,4
6,4
5,4
7,4
6,4
1,4
6,4
2,4
6,4
3,4
6,4
4,4
6,4
5,4
6,4
6,4
6,4
7,4
7,4
1,4
7,4
2,4
7,4
3,4
7,4
4,4
7,4
5,4
7,4
6,4
7,4
7,4
S5
1,4
1,5
1,4
2,5
1,4
3,5
1,4
4,5
1,4
5,5
1,4
6,5
1,4
7,5
2,4
1,5
2,4
2,5
2,4
3,5
2,4
4,5
2,4
5,5
2,4
6,5
2,4
7,5
3,4
1,5
3,4
2,5
3,4
3,5
3,4
4,5
3,4
5,5
3,4
6,5
3,4
7,5
4,4
1,5
4,4
2,5
4,4
3,5
4,4
4,5
4,4
5,5
4,4
6,5
4,4
7,5
5,4
1,5
5,4
2,5
5,4
3,5
5,4
4,5
5,4
5,5
5,4
6,5
5,4
7,5
6,4
1,5
6,4
2,5
6,4
3,5
6,4
4,5
6,4
5,5
6,4
6,5
6,4
7,5
7,4
1,5
7,4
2,5
7,4
3,5
7,4
4,5
7,4
5,5
7,4
6,5
7,4
7,5
S6
1,4
1,6
1,4
2,6
1,4
3,6
1,4
4,6
1,4
5,6
1,4
6,6
1,4
7,6
2,4
1,6
2,4
2,6
2,4
3,6
2,4
4,6
2,4
5,6
2,4
6,6
2,4
7,6
3,4
1,6
3,4
2,6
3,4
3,6
3,4
4,6
3,4
5,6
3,4
6,6
3,4
7,6
4,4
1,6
4,4
2,6
4,4
3,6
4,4
4,6
4,4
5,6
4,4
6,6
4,4
7,6
5,4
1,6
5,4
2,6
5,4
3,6
5,4
4,6
5,4
5,6
5,4
6,6
5,4
7,6
6,4
1,6
6,4
2,6
6,4
3,6
6,4
4,6
6,4
5,6
6,4
6,6
6,4
7,6
7,4
1,6
7,4
2,6
7,4
3,6
7,4
4,6
7,4
5,6
7,4
6,6
7,4
7,6
S7
1,4
1,7
1,4
2,7
1,4
3,7
1,4
4,7
1,4
5,7
1,4
6,7
1,4
7,7
2,4
1,7
2,4
2,7
2,4
3,7
2,4
4,7
2,4
5,7
2,4
6,7
2,4
7,7
3,4
1,7
3,4
2,7
3,4
3,7
3,4
4,7
3,4
5,7
3,4
6,7
3,4
7,7
4,4
1,7
4,4
2,7
4,4
3,7
4,4
4,7
4,4
5,7
4,4
6,7
4,4
7,7
5,4
1,7
5,4
2,7
5,4
3,7
5,4
4,7
5,4
5,7
5,4
6,7
5,4
7,7
6,4
1,7
6,4
2,7
6,4
3,7
6,4
4,7
6,4
5,7
6,4
6,7
6,4
7,7
7,4
1,7
7,4
2,7
7,4
3,7
7,4
4,7
7,4
5,7
7,4
6,7
7,4
7,7
Q5
S1
1,5
1,1
1,5
2,1
1,5
3,1
1,5
4,1
1,5
5,1
1,5
6,1
1,5
7,1
2,5
1,1
2,5
2,1
2,5
3,1
2,5
4,1
2,5
5,1
2,5
6,1
2,5
7,1
3,5
1,1
3,5
2,1
3,5
3,1
3,5
4,1
3,5
5,1
3,5
6,1
3,5
7,1
4,5
1,1
4,5
2,1
4,5
3,1
4,5
4,1
4,5
5,1
4,5
6,1
4,5
7,1
5,5
1,1
5,5
2,1
5,5
3,1
5,5
4,1
5,5
5,1
5,5
6,1
5,5
7,1
6,5
1,1
6,5
2,1
6,5
3,1
6,5
4,1
6,5
5,1
6,5
6,1
6,5
7,1
7,5
1,1
7,5
2,1
7,5
3,1
7,5
4,1
7,5
5,1
7,5
6,1
7,5
7,1
S2
1,5
1,2
1,5
2,2
1,5
3,2
1,5
4,2
1,5
5,2
1,5
6,2
1,5
7,2
2,5
1,2
2,5
2,2
2,5
3,2
2,5
4,2
2,5
5,2
2,5
6,2
2,5
7,2
3,5
1,2
3,5
2,2
3,5
3,2
3,5
4,2
3,5
5,2
3,5
6,2
3,5
7,2
4,5
1,2
4,5
2,2
4,5
3,2
4,5
4,2
4,5
5,2
4,5
6,2
4,5
7,2
5,5
1,2
5,5
2,2
5,5
3,2
5,5
4,2
5,5
5,2
5,5
6,2
5,5
7,2
6,5
1,2
6,5
2,2
6,5
3,2
6,5
4,2
6,5
5,2
6,5
6,2
6,5
7,2
7,5
1,2
7,5
2,2
7,5
3,2
7,5
4,2
7,5
5,2
7,5
6,2
7,5
7,2
S3
1,5
1,3
1,5
2,3
1,5
3,3
1,5
4,3
1,5
5,3
1,5
6,3
1,5
7,3
2,5
1,3
2,5
2,3
2,5
3,3
2,5
4,3
2,5
5,3
2,5
6,3
2,5
7,3
3,5
1,3
3,5
2,3
3,5
3,3
3,5
4,3
3,5
5,3
3,5
6,3
3,5
7,3
4,5
1,3
4,5
2,3
4,5
3,3
4,5
4,3
4,5
5,3
4,5
6,3
4,5
7,3
5,5
1,3
5,5
2,3
5,5
3,3
5,5
4,3
5,5
5,3
5,5
6,3
5,5
7,3
6,5
1,3
6,5
2,3
6,5
3,3
6,5
4,3
6,5
5,3
6,5
6,3
6,5
7,3
7,5
1,3
7,5
2,3
7,5
3,3
7,5
4,3
7,5
5,3
7,5
6,3
7,5
7,3
S4
1,5
1,4
1,5
2,4
1,5
3,4
1,5
4,4
1,5
5,4
1,5
6,4
1,5
7,4
2,5
1,4
2,5
2,4
2,5
3,4
2,5
4,4
2,5
5,4
2,5
6,4
2,5
7,4
3,5
1,4
3,5
2,4
3,5
3,4
3,5
4,4
3,5
5,4
3,5
6,4
3,5
7,4
4,5
1,4
4,5
2,4
4,5
3,4
4,5
4,4
4,5
5,4
4,5
6,4
4,5
7,4
5,5
1,4
5,5
2,4
5,5
3,4
5,5
4,4
5,5
5,4
5,5
6,4
5,5
7,4
6,5
1,4
6,5
2,4
6,5
3,4
6,5
4,4
6,5
5,4
6,5
6,4
6,5
7,4
7,5
1,4
7,5
2,4
7,5
3,4
7,5
4,4
7,5
5,4
7,5
6,4
7,5
7,4
S5
1,5
1,5
1,5
2,5
1,5
3,5
1,5
4,5
1,5
5,5
1,5
6,5
1,5
7,5
2,5
1,5
2,5
2,5
2,5
3,5
2,5
4,5
2,5
5,5
2,5
6,5
2,5
7,5
3,5
1,5
3,5
2,5
3,5
3,5
3,5
4,5
3,5
5,5
3,5
6,5
3,5
7,5
4,5
1,5
4,5
2,5
4,5
3,5
4,5
4,5
4,5
5,5
4,5
6,5
4,5
7,5
5,5
1,5
5,5
2,5
5,5
3,5
5,5
4,5
5,5
5,5
5,5
6,5
5,5
7,5
6,5
1,5
6,5
2,5
6,5
3,5
6,5
4,5
6,5
5,5
6,5
6,5
6,5
7,5
7,5
1,5
7,5
2,5
7,5
3,5
7,5
4,5
7,5
5,5
7,5
6,5
7,5
7,5
S6
1,5
1,6
1,5
2,6
1,5
3,6
1,5
4,6
1,5
5,6
1,5
6,6
1,5
7,6
2,5
1,6
2,5
2,6
2,5
3,6
2,5
4,6
2,5
5,6
2,5
6,6
2,5
7,6
3,5
1,6
3,5
2,6
3,5
3,6
3,5
4,6
3,5
5,6
3,5
6,6
3,5
7,6
4,5
1,6
4,5
2,6
4,5
3,6
4,5
4,6
4,5
5,6
4,5
6,6
4,5
7,6
5,5
1,6
5,5
2,6
5,5
3,6
5,5
4,6
5,5
5,6
5,5
6,6
5,5
7,6
6,5
1,6
6,5
2,6
6,5
3,6
6,5
4,6
6,5
5,6
6,5
6,6
6,5
7,6
7,5
1,6
7,5
2,6
7,5
3,6
7,5
4,6
7,5
5,6
7,5
6,6
7,5
7,6
S7
1,5
1,7
1,5
2,7
1,5
3,7
1,5
4,7
1,5
5,7
1,5
6,7
1,5
7,7
2,5
1,7
2,5
2,7
2,5
3,7
2,5
4,7
2,5
5,7
2,5
6,7
2,5
7,7
3,5
1,7
3,5
2,7
3,5
3,7
3,5
4,7
3,5
5,7
3,5
6,7
3,5
7,7
4,5
1,7
4,5
2,7
4,5
3,7
4,5
4,7
4,5
5,7
4,5
6,7
4,5
7,7
5,5
1,7
5,5
2,7
5,5
3,7
5,5
4,7
5,5
5,7
5,5
6,7
5,5
7,7
6,5
1,7
6,5
2,7
6,5
3,7
6,5
4,7
6,5
5,7
6,5
6,7
6,5
7,7
7,5
1,7
7,5
2,7
7,5
3,7
7,5
4,7
7,5
5,7
7,5
6,7
7,5
7,7
Q6
S1
1,6
1,1
1,6
2,1
1,6
3,1
1,6
4,1
1,6
5,1
1,6
6,1
1,6
7,1
2,6
1,1
2,6
2,1
2,6
3,1
2,6
4,1
2,6
5,1
2,6
6,1
2,6
7,1
3,6
1,1
3,6
2,1
3,6
3,1
3,6
4,1
3,6
5,1
3,6
6,1
3,6
7,1
4,6
1,1
4,6
2,1
4,6
3,1
4,6
4,1
4,6
5,1
4,6
6,1
4,6
7,1
5,6
1,1
5,6
2,1
5,6
3,1
5,6
4,1
5,6
5,1
5,6
6,1
5,6
7,1
6,6
1,1
6,6
2,1
6,6
3,1
6,6
4,1
6,6
5,1
6,6
6,1
6,6
7,1
7,6
1,1
7,6
2,1
7,6
3,1
7,6
4,1
7,6
5,1
7,6
6,1
7,6
7,1
S2
1,6
1,2
1,6
2,2
1,6
3,2
1,6
4,2
1,6
5,2
1,6
6,2
1,6
7,2
2,6
1,2
2,6
2,2
2,6
3,2
2,6
4,2
2,6
5,2
2,6
6,2
2,6
7,2
3,6
1,2
3,6
2,2
3,6
3,2
3,6
4,2
3,6
5,2
3,6
6,2
3,6
7,2
4,6
1,2
4,6
2,2
4,6
3,2
4,6
4,2
4,6
5,2
4,6
6,2
4,6
7,2
5,6
1,2
5,6
2,2
5,6
3,2
5,6
4,2
5,6
5,2
5,6
6,2
5,6
7,2
6,6
1,2
6,6
2,2
6,6
3,2
6,6
4,2
6,6
5,2
6,6
6,2
6,6
7,2
7,6
1,2
7,6
2,2
7,6
3,2
7,6
4,2
7,6
5,2
7,6
6,2
7,6
7,2
S3
1,6
1,3
1,6
2,3
1,6
3,3
1,6
4,3
1,6
5,3
1,6
6,3
1,6
7,3
2,6
1,3
2,6
2,3
2,6
3,3
2,6
4,3
2,6
5,3
2,6
6,3
2,6
7,3
3,6
1,3
3,6
2,3
3,6
3,3
3,6
4,3
3,6
5,3
3,6
6,3
3,6
7,3
4,6
1,3
4,6
2,3
4,6
3,3
4,6
4,3
4,6
5,3
4,6
6,3
4,6
7,3
5,6
1,3
5,6
2,3
5,6
3,3
5,6
4,3
5,6
5,3
5,6
6,3
5,6
7,3
6,6
1,3
6,6
2,3
6,6
3,3
6,6
4,3
6,6
5,3
6,6
6,3
6,6
7,3
7,6
1,3
7,6
2,3
7,6
3,3
7,6
4,3
7,6
5,3
7,6
6,3
7,6
7,3
S4
1,6
1,4
1,6
2,4
1,6
3,4
1,6
4,4
1,6
5,4
1,6
6,4
1,6
7,4
2,6
1,4
2,6
2,4
2,6
3,4
2,6
4,4
2,6
5,4
2,6
6,4
2,6
7,4
3,6
1,4
3,6
2,4
3,6
3,4
3,6
4,4
3,6
5,4
3,6
6,4
3,6
7,4
4,6
1,4
4,6
2,4
4,6
3,4
4,6
4,4
4,6
5,4
4,6
6,4
4,6
7,4
5,6
1,4
5,6
2,4
5,6
3,4
5,6
4,4
5,6
5,4
5,6
6,4
5,6
7,4
6,6
1,4
6,6
2,4
6,6
3,4
6,6
4,4
6,6
5,4
6,6
6,4
6,6
7,4
7,6
1,4
7,6
2,4
7,6
3,4
7,6
4,4
7,6
5,4
7,6
6,4
7,6
7,4
S5
1,6
1,5
1,6
2,5
1,6
3,5
1,6
4,5
1,6
5,5
1,6
6,5
1,6
7,5
2,6
1,5
2,6
2,5
2,6
3,5
2,6
4,5
2,6
5,5
2,6
6,5
2,6
7,5
3,6
1,5
3,6
2,5
3,6
3,5
3,6
4,5
3,6
5,5
3,6
6,5
3,6
7,5
4,6
1,5
4,6
2,5
4,6
3,5
4,6
4,5
4,6
5,5
4,6
6,5
4,6
7,5
5,6
1,5
5,6
2,5
5,6
3,5
5,6
4,5
5,6
5,5
5,6
6,5
5,6
7,5
6,6
1,5
6,6
2,5
6,6
3,5
6,6
4,5
6,6
5,5
6,6
6,5
6,6
7,5
7,6
1,5
7,6
2,5
7,6
3,5
7,6
4,5
7,6
5,5
7,6
6,5
7,6
7,5
S6
1,6
1,6
1,6
2,6
1,6
3,6
1,6
4,6
1,6
5,6
1,6
6,6
1,6
7,6
2,6
1,6
2,6
2,6
2,6
3,6
2,6
4,6
2,6
5,6
2,6
6,6
2,6
7,6
3,6
1,6
3,6
2,6
3,6
3,6
3,6
4,6
3,6
5,6
3,6
6,6
3,6
7,6
4,6
1,6
4,6
2,6
4,6
3,6
4,6
4,6
4,6
5,6
4,6
6,6
4,6
7,6
5,6
1,6
5,6
2,6
5,6
3,6
5,6
4,6
5,6
5,6
5,6
6,6
5,6
7,6
6,6
1,6
6,6
2,6
6,6
3,6
6,6
4,6
6,6
5,6
6,6
6,6
6,6
7,6
7,6
1,6
7,6
2,6
7,6
3,6
7,6
4,6
7,6
5,6
7,6
6,6
7,6
7,6
S7
1,6
1,7
1,6
2,7
1,6
3,7
1,6
4,7
1,6
5,7
1,6
6,7
1,6
7,7
2,6
1,7
2,6
2,7
2,6
3,7
2,6
4,7
2,6
5,7
2,6
6,7
2,6
7,7
3,6
1,7
3,6
2,7
3,6
3,7
3,6
4,7
3,6
5,7
3,6
6,7
3,6
7,7
4,6
1,7
4,6
2,7
4,6
3,7
4,6
4,7
4,6
5,7
4,6
6,7
4,6
7,7
5,6
1,7
5,6
2,7
5,6
3,7
5,6
4,7
5,6
5,7
5,6
6,7
5,6
7,7
6,6
1,7
6,6
2,7
6,6
3,7
6,6
4,7
6,6
5,7
6,6
6,7
6,6
7,7
7,6
1,7
7,6
2,7
7,6
3,7
7,6
4,7
7,6
5,7
7,6
6,7
7,6
7,7
Q7
S1
1,7
1,1
1,7
2,1
1,7
3,1
1,7
4,1
1,7
5,1
1,7
6,1
1,7
7,1
2,7
1,1
2,7
2,1
2,7
3,1
2,7
4,1
2,7
5,1
2,7
6,1
2,7
7,1
3,7
1,1
3,7
2,1
3,7
3,1
3,7
4,1
3,7
5,1
3,7
6,1
3,7
7,1
4,7
1,1
4,7
2,1
4,7
3,1
4,7
4,1
4,7
5,1
4,7
6,1
4,7
7,1
5,7
1,1
5,7
2,1
5,7
3,1
5,7
4,1
5,7
5,1
5,7
6,1
5,7
7,1
6,7
1,1
6,7
2,1
6,7
3,1
6,7
4,1
6,7
5,1
6,7
6,1
6,7
7,1
7,7
1,1
7,7
2,1
7,7
3,1
7,7
4,1
7,7
5,1
7,7
6,1
7,7
7,1
S2
1,7
1,2
1,7
2,2
1,7
3,2
1,7
4,2
1,7
5,2
1,7
6,2
1,7
7,2
2,7
1,2
2,7
2,2
2,7
3,2
2,7
4,2
2,7
5,2
2,7
6,2
2,7
7,2
3,7
1,2
3,7
2,2
3,7
3,2
3,7
4,2
3,7
5,2
3,7
6,2
3,7
7,2
4,7
1,2
4,7
2,2
4,7
3,2
4,7
4,2
4,7
5,2
4,7
6,2
4,7
7,2
5,7
1,2
5,7
2,2
5,7
3,2
5,7
4,2
5,7
5,2
5,7
6,2
5,7
7,2
6,7
1,2
6,7
2,2
6,7
3,2
6,7
4,2
6,7
5,2
6,7
6,2
6,7
7,2
7,7
1,2
7,7
2,2
7,7
3,2
7,7
4,2
7,7
5,2
7,7
6,2
7,7
7,2
S3
1,7
1,3
1,7
2,3
1,7
3,3
1,7
4,3
1,7
5,3
1,7
6,3
1,7
7,3
2,7
1,3
2,7
2,3
2,7
3,3
2,7
4,3
2,7
5,3
2,7
6,3
2,7
7,3
3,7
1,3
3,7
2,3
3,7
3,3
3,7
4,3
3,7
5,3
3,7
6,3
3,7
7,3
4,7
1,3
4,7
2,3
4,7
3,3
4,7
4,3
4,7
5,3
4,7
6,3
4,7
7,3
5,7
1,3
5,7
2,3
5,7
3,3
5,7
4,3
5,7
5,3
5,7
6,3
5,7
7,3
6,7
1,3
6,7
2,3
6,7
3,3
6,7
4,3
6,7
5,3
6,7
6,3
6,7
7,3
7,7
1,3
7,7
2,3
7,7
3,3
7,7
4,3
7,7
5,3
7,7
6,3
7,7
7,3
S4
1,7
1,4
1,7
2,4
1,7
3,4
1,7
4,4
1,7
5,4
1,7
6,4
1,7
7,4
2,7
1,4
2,7
2,4
2,7
3,4
2,7
4,4
2,7
5,4
2,7
6,4
2,7
7,4
3,7
1,4
3,7
2,4
3,7
3,4
3,7
4,4
3,7
5,4
3,7
6,4
3,7
7,4
4,7
1,4
4,7
2,4
4,7
3,4
4,7
4,4
4,7
5,4
4,7
6,4
4,7
7,4
5,7
1,4
5,7
2,4
5,7
3,4
5,7
4,4
5,7
5,4
5,7
6,4
5,7
7,4
6,7
1,4
6,7
2,4
6,7
3,4
6,7
4,4
6,7
5,4
6,7
6,4
6,7
7,4
7,7
1,4
7,7
2,4
7,7
3,4
7,7
4,4
7,7
5,4
7,7
6,4
7,7
7,4
S5
1,7
1,5
1,7
2,5
1,7
3,5
1,7
4,5
1,7
5,5
1,7
6,5
1,7
7,5
2,7
1,5
2,7
2,5
2,7
3,5
2,7
4,5
2,7
5,5
2,7
6,5
2,7
7,5
3,7
1,5
3,7
2,5
3,7
3,5
3,7
4,5
3,7
5,5
3,7
6,5
3,7
7,5
4,7
1,5
4,7
2,5
4,7
3,5
4,7
4,5
4,7
5,5
4,7
6,5
4,7
7,5
5,7
1,5
5,7
2,5
5,7
3,5
5,7
4,5
5,7
5,5
5,7
6,5
5,7
7,5
6,7
1,5
6,7
2,5
6,7
3,5
6,7
4,5
6,7
5,5
6,7
6,5
6,7
7,5
7,7
1,5
7,7
2,5
7,7
3,5
7,7
4,5
7,7
5,5
7,7
6,5
7,7
7,5
S6
1,7
1,6
1,7
2,6
1,7
3,6
1,7
4,6
1,7
5,6
1,7
6,6
1,7
7,6
2,7
1,6
2,7
2,6
2,7
3,6
2,7
4,6
2,7
5,6
2,7
6,6
2,7
7,6
3,7
1,6
3,7
2,6
3,7
3,6
3,7
4,6
3,7
5,6
3,7
6,6
3,7
7,6
4,7
1,6
4,7
2,6
4,7
3,6
4,7
4,6
4,7
5,6
4,7
6,6
4,7
7,6
5,7
1,6
5,7
2,6
5,7
3,6
5,7
4,6
5,7
5,6
5,7
6,6
5,7
7,6
6,7
1,6
6,7
2,6
6,7
3,6
6,7
4,6
6,7
5,6
6,7
6,6
6,7
7,6
7,7
1,6
7,7
2,6
7,7
3,6
7,7
4,6
7,7
5,6
7,7
6,6
7,7
7,6
S7
1,7
1,7
1,7
2,7
1,7
3,7
1,7
4,7
1,7
5,7
1,7
6,7
1,7
7,7
2,7
1,7
2,7
2,7
2,7
3,7
2,7
4,7
2,7
5,7
2,7
6,7
2,7
7,7
3,7
1,7
3,7
2,7
3,7
3,7
3,7
4,7
3,7
5,7
3,7
6,7
3,7
7,7
4,7
1,7
4,7
2,7
4,7
3,7
4,7
4,7
4,7
5,7
4,7
6,7
4,7
7,7
5,7
1,7
5,7
2,7
5,7
3,7
5,7
4,7
5,7
5,7
5,7
6,7
5,7
7,7
6,7
1,7
6,7
2,7
6,7
3,7
6,7
4,7
6,7
5,7
6,7
6,7
6,7
7,7
7,7
1,7
7,7
2,7
7,7
3,7
7,7
4,7
7,7
5,7
7,7
6,7
7,7
7,7
The upper pair of numbers are the quadrant X,Y coordinates.
The lower pair of numbers are the sector X,Y coordinates.
In the game, objects are represented thusly on the long-range scanner ("galaxy display"):
1st number = number of aliens in quadrant
2nd number = number of space stations in quadrant
3rd number = number of stars in quadrant
In the game, objects are represented thusly on the short-range scanner:
<O> = position of your ship
+++ = position of enemy ship (alien)
H = position of space station
* = position of star
These issues are known, under Ami/WinArcadia 34.01, at least. The reasons for these issues have not yet been investigated.
For the
PIPBUG version only:
The energy display can be incorrect (eg. "08VU", "15\\", etc.).
When firing phasors, the user input prompts are not shown.
For the
BINBUG versions only:
The galaxy display is prepended with junk.
Commands are:
0: Move (specify a direction ("course") and distance ("warp factor") in sectors)
1: Short range scan & status
2: Long range scan ("galaxy display")
3: Transfer energy to shield ("shield energy transfer")
4: Fire phasor (specify energy)
5: Fire torpedo (specify direction)
Directions are:
| 06 | 05 | 04 | 03 | 02 |
| 07 | 01 | |||
| 08 | 00 | |||
| 09 | 15 | |||
| 10 | 11 | 12 | 13 | 14 |
Game variables are as follows. All are numbers in ASCII format ('0'..'9') (eg. the value 1234 is represented as $31 $32 $33 $34):
| Address(es) | Description | Range |
| $60C..$60D | stardate (ie. time remaining) | 00..99 |
| $62B | quadrant X | 1..7 |
| $62D | quadrant Y | 1..7 |
| $63A | sector X | 1..7 |
| $63C | sector Y | 1..7 |
| $649..$64C | energy | 0000..9999 |
| $659 | torpedos | 0..9 |
| $666..$669 | shields | 0000..9999 |
| $917..$947 | aliens in each of the 49 quadrants | 0..9 |
| $948..$978 | space stations in each of the 49 quadrants | 0..9 |
| $979..$9A9 | stars in each of the 49 quadrants | 0..9 |
Binary Floating Point Routines (Application Note AS57):
The program's prompt is corrupt (maybe the emulated teletype is not ready
for it).
Each pair of hex digits is not shown until it has been completely input.
The spaces around operators are added automatically by the program rather
than by the user.
The start address determines the rounding mode, as follows:
G6A6 will run with rounding.
G6AA will run without rounding.
Give 8 hex digits, then an operator, then another 8 hex digits, then =
Supported operators are +, -, * and : (which is division).
Biorhythm:
Dates are expected to be in dd/mm/yy format.
Invalid dates will cause the program to hang.
Bit Echo:
Prints flashing garbage after each letter, for some reason.
Cricket:
Doesn't randomize very well, for some reason.
DG640 Driver:
To get the flashing cursor, you need PIPBUG (not BINBUG).
ETI-685 Memory Tester:
This expects BINBUG 6.1. It is used as follows:
G440
where 1. At the "PLAYER 1-" prompt:
2. For each additional player you want to add:
3. Press ENTER to begin.
4. For each player:
5. Watch the race and then press ENTER.
6. Go to 4.
This program requires extra hardware (eg. various motors), which is not
emulated by Ami/WinPIPBUG. Although it will load and run, it will
not do anything useful on the emulators, and, intentionally, does not
produce output on the screen. Also, it expects a data table (starting at
!6000), which is not present.
"When called, the program will wait until you enter any character. It will
then generate a random number between 1 and 99, which you must guess.
Starting address is $0440."
Enter source address (2 hex digits).
Here is the map:
Rooms 1 and E are connected.
"Life is a matrix game concerned with the life, death and birth of cells.
Imagine each cell to be in a two-dimensional linear matrix, such that each
cell location has eight possible neighbours, as shown:
The rules of cell life, death and birth are as follows:
1. A live cell will survive if it has two or three live neighbours.
To work with practical terminals the program operates with a limited size
matrix, but makes it effectively "infinite" by having "wrap around" from
side to side and from top to bottom.
and then switch to the appropriate baud rate (110 or 300 baud). Then
type a U for 110 baud operation, or a Y for 300 baud operation.
..O. GENERATION 2
.OO. GENERATION 3
.OO. GENERATION 4
.OO. GENERATION 5
One of the most interesting and simple patterns has been named the
"Glider". The seed for this is shown below:
If you are running Life at 1200 baud, it is better to use the autoprint
version, which prints out after every generation, and stops automatically
when the pattern stabilises.
For 110 baud, you just need to press U, as documented.
$C00..$C59: baud rate initialization routine?
LIFECOUT has the following side effects when called:
LIFECHIN has the following side effects when called:
This program requires extra hardware, eg. light pen, which is not
supported by Ami/WinPIPBUG. Although it will load and run, it will
not do anything useful on the emulators, and, apparently intentionally,
does not produce output on the screen.
F = Fuel (out of 40)
The * is a graphical indicator of your distance from the surface.
The pseudocode is:
Your burn will not take effect until the turn after you make it.
You need to use Ctrl-L instead of ENTER after each line of input.
"This program provides the functions of a simple, 3-function calculator.
It will multiply, add or subtract two single digit decimal numbers. Normal
plus, minus and equals signs are used, with an asterisk symbol for
multiplication. Starts at $0440."
Note that the listing is self-contradictory (the
machine code bytes do not match the assembly source code).
SUBT:
MULT: // $48E
SUB1:
ZEND:
You use the program as follows:
where <loops> is "01".."7F". ("80".."$FF" give infinite tests.)
Eg.:
If there is no resulting output other than linefeeds (just goes back to
the "*" prompt), this indicates success.
Z or S mean that cleared (zeroed) memory did not read back as $00.
The address of the error then follows the error code.
"Upon being called, this program will give a prompt character, and await a
command character. Commands:
T allows a message to be entered
In text input mode, the DEL character acts as a destructive
backspace for correcting errors. To return to command mode, type an Esc.
Due to its length, this has now been split off into a
separate document.
Note that this is *not* byte-for-byte identical to the official PIPBUG release
of MicroWorld BASIC, as evidenced by the fact that eg. the official BINBUG
patch (aka "personality module") for it will not work. The available dump
was originally for PIPBUG, then was ported to PHUNSY, then was ported back to
PIPBUG.
You must type 6 consecutive hex digits. These are not echoed to the
screen (except that Ami/WinArcadia do this for you). The first 4
digits are the starting address (including any leading zeroes) and the
last 2 digits are the least significant byte of the ending address (the
most significant byte is always the same as that of the starting address).
Eg.:
will disassemble $440..$4FF.
To disassemble another region, type:
at the command prompt ("*"). If you get another "*", retry; otherwise,
now enter a new 6-digit address range.
"The "Music" program occupies locations $4A0 to $5D3, and uses PIPBUG
routines. It contains absolute addresses, and is not easily relocated. The
music is generated at the flag output of the 2650, and some form of audio
transducer is required. This can simply be an audio amplifier and speaker,
connected via a suitable attenuator, to the buffered flag output of the
CPU.
The last two parameters are optional. If they are not given, the program
will use the previous values. Thus, to play "Yankee Doodle", type:
and for "Bach", type:
These print garbage while playing, for some reason.
For the purposes of the above table, each "octave" is assumed to begin at
E.
"The game of Nim: starting with 23 you and the program take turns at
subtracting a number from 1 to 3. The one that leaves 1 after their move
wins. Starting address is $0440."
The ! prompt means to hit ENTER (it presumably uses this user-dependant
delay for randomization).
The original published version has a bug at $505 ($00 should be $0C).
There is a fixed version in the Games Pack.
This program needs the starting time to be poked into memory and registers
before execution.
Pause the machine and then set the time like this before starting at $500:
When the time reaches 13:00, it will reset back to 01:00
(ie. it is a 12-hour rather than a 24-hour clock).
Input must be in Y,X (row,col) format.
Of course, the provided binaries do nothing (ie. do not "work") by
themselves, as they are only subroutines. See the relevant magazine
articles for more information about how to use them in your own programs.
You have to react when the cursor is in the leftmost column.
Enter source address (4 hex digits).
"The computer generates a 4*4 array of the first 16 letters of the
alphabet, arranged in a random order. The object of the game is to
rearrange the array into the following form:
The array can only be rearranged by rotating [2*2] blocks of four letters
clockwise. The block to be rotated is specified by the letter in its top
left hand corner. It is invalid to try to rotate by calling letters on
either the bottom row or the right hand column of the array.
and the computer will respond with "PRESS ANY KEY". Once this has been
done, a random pattern will be generated and printed, and the prompt
message "ROTATE:" given.
PRESS ANY KEY
OJMD
ROTATE: F
OJMD
ROTATE: N
OJMD
ROTATE: N
OJMD
ROTATE: F
OJMD
ROTATE: EXCHANGE: L,M
OJLD
ROTATE: P
OJLD
ROTATE: M
OJLD
ROTATE: CANCEL
OJLD
ROTATE: G
OJLD
ROTATE: YOU TOOK 07 MOVES If you wish to rotate a particular block, type the letter in the top left
hand corner of that block. If you wish to cancel a move, type carriage
return, and the program will respond with "CANCEL", and then reprint the
last but one block.
This program does not echo your input to the screen.
This game expects a display with more than 16 rows.
The objective is to reach the end configuration shown below in as few
moves as possible, by shooting stars. Each move consists of a digit 1-9
corresponding to the position of the star to shoot:
The only valid first move is 5. Shots have these results:
. means the star becomes a dot
This program uses cycle counting techniques. Under Ami/WinArcadia 8.41,
it appears to run too fast (ie. the "game" time goes faster
than the emulator time).
This program expects extra input (eg. various sensors) and output (eg.
pitch and roll indicators) hardware, which is not supported by
Ami/WinPIPBUG. (The LED display, used for output of heading data, is
supported.) Although it will load and run, it will not do anything useful
on the emulators, and, intentionally, does not produce output on the main
screen (only via the LED display).
This machine is a "microprocessor development board" aka "trainer".
MON, RST and ENT NXT are white on orange. All other keys are white on
blue. There are no paddles.
Each of the 8 digits is divided into 8 segments, as shown:
+0+ The + don't really exist, therefore it is really like this:
5 1
+6+ 0
4 2 5 1
+3+ 7 6
4 2
3 7
Eg. the bottom segment is controlled by bit 3 (so, $08 would set it, $00
would clear it).
The display is controllable at the segment level (ie. you can get 256
combinations) via direct hardware access (ie. bypassing USE BIOS functions
and using the WRTE instruction), using the bit numbers listed above.
In NON-EXTENDED I/O mode:
REDD,rn to read from the toggle switches
In EXTENDED I/O mode:
REDE,rn $07 to read from the toggle switches
In MEMORY MAPPED I/O mode:
LODA,rn $0FFF to read from the toggle switches
"It appears to be on all the time. It is on in monitor
mode, during stepping, and remains on at breakpoints. It will turn off
after the processor executes a HALT ($40) instruction. It won't turn
back on again until you hit MON, RST, in that order. You can't just
break back into monitor mode after hitting a HALT instruction. Hitting
MON, RST somehow brings the machine back to life and into monitor mode;
otherwise the machine is dark." - Tyler Whitney.
When an interrupt is generated/received, the Instructor 50
writes $07 or $87 to the data bus, depending on the position of the
DIRECT/INDIRECT INTERRUPT switch. Then it does a ZBSR $07 or ZBSR *$07, as
appropriate.
"A.C. LINE" (ie. 50Hz) or
The cassette subsystem is somewhat like that of the Elektor TV Games
Computer, but uses 6 pulses for a "0" and 3 pulses for a "1", except that
3 extra pulses are appended to the last bit of each byte (giving 6+3=9
pulses for a "0" or 3+3=6 pulses for a "1").
USE is an acronym for "User System Executive".
"When in Monitor mode, pressing anything on the hex keypad generates
Error 2 on the real machine. On the control keypad, you can hit most keys
with impunity. Hitting STEP while in monitor mode generates Error 9 on the
real machine." - Tyler Whitney.
The USRDSP (USeR DiSPlay) command is used as follows:
R0: Return code.
Note the trailing dots for "b." and "d.".
Beat the Odds:
You can make a bet on any of the following results:
Note that in the table above, the bet "6..8 lamps lit" is listed twice, with different odds. This is authentic to the original Signetics documentation.
This game is intended to be played by multiple humans using real money.
One player would act as the "house" (ie. banker/dealer) and call for bets, take and record wagers, operate the computer, and pay winners according to the above odds.
The computer is used merely as a randomizer. There is no loG440 1000 1FFF
Funny Farm Races:
Type in the name of the first player and press ENTER.
Press P. The machine will say "PLAYER 2-" (or whatever).
Type in the name of the player and then press ENTER.
The machine will ask "BET?".
For each bet you want to place:
a. Press Y and then press ENTER.
b. The machine will ask "DOG NO?".
c. Press the number (0..9) of your preferred dog and then press ENTER.
d. The machine will ask "HOW MUCH?".
Press N when this player has placed all their bets.
Furnace:
Guessing Game (machine code version):
STRT = $440 code
INPT = $493 code
PRNT = $4A6 code
MSAG = $4B1 data
HexCal aka HexCalc:
/ appears.
Enter destination address (2 hex digits).
= and result appears.
The first digit of each pair entered is not echoed to the display until the
second digit has been input.
Result is the relative offset (ie. the distance between the addresses). Eg.:
01/02=01
03/04=7F
05/05=00
20/30=10PAIR equ $45E
gosub CRLF;
for (r1 = 3; r1 >= 1; r1--)
{
PAIR = BINOUT();
COUT('/');
PAIR = (BINOUT() - PAIR) & $7F;
COUT('=');
BOUT(PAIR); // Byte output in hex
COUT(' ');
}
goto $3F00;
BINOUT: ;$46D
// Input two hex chars and output in hex
*($476) = BIN(); // Input two hex chars and form as byte
BOUT(*($476)); // Byte output in hex
return *($476);
Hunt the Wumpus:
----0----
/ / \ \
--2---5---8---B--
/ | | | | \
(E)<---1---3---6---9---C---E--->(1)
\ | | | | /
--4---7---A---D--
\ \ / /
----F----
Room
0
1
2
3
4
5
6
7
8
9
A
B
C
D
E
F
0
2
5
8
B
1
2
3
4
E
2
0
1
3
5
3
1
2
4
6
4
1
3
7
F
5
0
2
6
8
6
3
5
7
9
7
4
6
A
F
8
0
5
9
B
9
6
8
A
C
A
7
9
D
F
B
0
8
C
E
C
9
B
D
E
D
A
C
E
F
E
1
B
C
D
F
4
7
A
D
Life-MachineCode:
1 2 3
4 X 5
6 7 8
2. A live cell will die if it has less than two or more than three
live neighbours.
3. A birth in an empty cell will occur if it has exactly three live
neighbours.
4. Births and deaths take place simultaneously.
In our version of Life, live cells are represented by Os, and dead or
empty cells as blanks. The program starts with an initial pattern (fed in
by the player), and calculates the new patterns "generation by
generation".
The 32*16 versions are intended for use with the Low Cost VDU of EA
February and April 1978. The 32*24 versions are intended for terminals
such as the EME-1 VDU, described in the EA January and February 1977
issues.
To use the program, type:
GC00<CR>
The program will respond with the word "LIFE", followed by the prompt
character ":".
If you respond with "N", the program will expect a new matrix to be
supplied. The program will echo the N, followed by a carriage return and
line feed. A pattern may then be written in (or "seeded") by using the
space bar for blanks (these are printed as dots), Os for live cells, and
line feeds (LF) [Ctrl+J in Ami/WinArcadia] for new lines.
Blanks are not required on the right hand side of the pattern. Carriage
return (CR) will permit overwriting of a line, allowing error correction.
Once your pattern is complete, use LFs if necessary to advance to the
bottom of the matrix.
Once the pattern is completed, the program will reprint it, and give
the prompt sign again. If you now respond with a Gxx, $xx generations
will be evolved, with a printout after the last generation. G00 will
produce printout after 256 generations, while G01 will produce a
printout after only one generation. And so on...
Immediately after you have typed in this command, the program will
respond with a message such as <15S, to indicate that in less than 15
seconds it will print out the result of the Gxx instruction. After
printing the result the new generation count and prompt will appear at
the bottom left hand corner of the screen. This may overwrite live cells,
so try and keep your patterns in the centre of the screen (patterns to the
right will wrap around to the left).
The remaining instruction is P, which causes the program to print out
the existing matrix. The instruction is not used a great deal.
This is the result of a simple pattern. This stabilises after four
generations, and then continues forever unchanged:
..O. GENERATION 1
OOO.
....
.OO.
.O..
.OO.
.OO.
O..O
.OO.
O..O
.OO..O.
..O
OOO
Simply feed in a starting pattern (using the N command), and sit back
and watch. The program will continue until a stable pattern is achieved,
at which time it will stop. Note, however, that it cannot detect recurring
cyclical patterns, so watch out for these. To stop them, you will have to
use the reset facility of the 2650."
For 300 baud, you need to press U (not Y), then ENTER, contrary to the
documentation.
Then press N for a new field and set it up with Os and
spaces, using Ctrl-J repeatedly to move down.
$C26: LIFECRLF
$C39: LIFECOUT
$C5A: LIFECHIN
$C76..$EEC: Life game code
$EED..$F54: Life game variables
PSL: CC = eq;
PSL: primary register bank (r1..r3) is always selected
PSU: Flag pin is always set
r1 = *(DATABUS);
r0 = r6 = 0;
You should not call it when SP > 4 (you need one level of stack for
LIFECOUT's return address, another level for LIFEDELAY's return address,
and another level for LIFEDELAY_ALT's return address.
PSL: CC = gt;
PSL: primary register bank (r1..r3) is always selected
PSL: With Carry bit is always clear
r0 = r4 = return code (1..127)
r5 = r6 = 0;
You should not call it when SP > 4 (you need one level of stack for
LIFECHIN's return address, another level for LIFEDELAY's return address,
and another level for LIFEDELAY_ALT's return address.
Linearization (Linearisatie):
Lunar Lander (machine code version):
V = Velocity (- is down (towards surface), + is up (away from surface))
D = Distance from surface (- is underground, + is above ground)
B = Burn
You must give a 2-digit burn each turn.
Neither digit is displayed until both have been entered.
Lunar Lander (2650 Micro BASIC version):
input fuel (F), velocity (V), height (D)
V = -V; // convert velocity from "down" (towards) to "up" (away from)
for (;;)
{ do
{ print fuel (F), velocity (V), height (D)
W = D; // ceiling = height
input burn (T)
D += V; // move lander
F -= T; // deduct burn from fuel
if (D > 150) G=-2; // G is the
elif (D > 100) G=-3; // gravity factor
elif (D > 50) G=-4; // (stronger closer
elif (D < 50) G=-5; // to surface)
else
{ assert(D == 50);
G (gravity factor) is uninitialized and will retain its
value from the previous turn or game (or zero for first run).
}
V += T + G; // velocity += burn + gravity factor (applied next turn)
K = -D * 100; // depth of crater = height below ground * 100
} while (D > 0 && D <= W); // still above ground but at or below ceiling
if (D > W) escaped gravity, game over
elif (D < 0) new crater, game over
else
{ assert(D == 0);
if (V > 0) moving away, continue game
elif (V == 0) perfect, game over
elif (V > -5) not bad, game over
elif (V > -10) damage sustained, game over
elif (V < -10) lander destroyed, game over
else
{ assert(V == -10);
no message given, game over
(result should really be damage sustained or lander destroyed)
} } }
Any movement away from the moon will be considered to have escaped gravity,
regardless of how near you are to it and how much fuel you have.
The weight of your fuel is not taken into consideration by the game.
Gravity is taken into consideration but not in an accurate way.
A good landing must have a height of exactly zero and a velocity (for
next turn) towards the moon as small as possible.
An example of an easy perfect (if unrealistic) landing would be to start
with 6 (or more) units of fuel, velocity down of 1, height of 1, burn of 6.
The game changes your height to 1 to 0, and your velocity up from -1 to 0
(it adds the burn of 6 and the gravity factor of -5 to it).
Mastermind, Revised Mastermind:
Maths Demonstration:
STRT:
*(MOD) = ADDZ r3;
r3 = SUB1();
for (;;)
{ r0 = CHIN();
if (r0 == '+') goto PLUS;
elif (r0 == '-') goto SUBT;
elif (r0 == '*') goto MULT;
}
*(MOD) = SUBZ r3;
PLUS: // $45C
gosub COUT(r0); // print operation symbol ('+' or '-')
r2 = r3; // 1st argument
r3 = SUB1(); // 2nd argument
r0 = r2; // 1st argument
MOD:
r0 += r3, or r0 -= r3, depending on the desired operation
if (r0 < 0)
{ r0 = r3 - r2;
*(A1) = '-'; // store '-' as 1st character
r0 |= $30; // format for display
*(A2) = r0; // store r0 as 2nd character
} elif (r0 >= 10)
{ *(A1) = '1'; // store '1' as 1st character
r0 -= 10;
r0 |= $30; // format for display
*(A2) = r0; // store r0 as 2nd character
} else
{ r0 |= $30; // format for display
*(A1) = r0; // store as 1st character
r0 = NUL;
*(A2) = r0 [NUL]; // store as 2nd character
}
goto ZEND;
gosub COUT(r0); // print operation symbol ('*')
r2 = r3; // 1st argument
r3 = SUB1(); // 2nd argument
r0 = 0;
while (r2 != 0)
{ r0 += r3;
r2--;
}
while (r0 >= 10)
{ r0 -= 10;
r2++;
}
r2 |= $30; // format for display
*(A1) = r2;
r0 |= $30; // format for display
*(A2) = r0;
goto ZEND;
do
{ r0 = CHIN();
clear With Carry and COMpare bits
} while (r0 < '0' || r0 > '9');
r3 = r0;
gosub COUT(r0);
r3 &= $0F; // remove display formatting
return r3;
r1 = 0;
while (*(MSAG + ++r1) != 0)
{ COUT(r0);
}
gosub CRLF;
goto STRT;
Memory Test:
G48F <start-address> <end-address> <loops>
G48F 0500 3FFF 7F
Errors are as follows:
W means that a single bit of memory (eg. $10) did not read back
correctly.
L means that set memory did not read back as $FF.
Message Editor:
C allows a stored message to be checked
R allows it to be repeated until the CPU is reset
If the message being stored is too long for the buffer, an F will be
displayed. Starts at $0440."
MicroByte Adventure:
MicroWorld BASIC:
The first command you should issue is OLD. Then you can RUN or LIST the
program.
Mini-Disassembler:
0440FF
Note that the mnemonics used are not always standard Signetics. Eg.:
HLT = HALT
LPU = LPSU
LPL = LPSL
PPU = PPSU
PPL = PPSLG440
There are bugs in the published program listing, causing incorrect
disassembly of some instructions. There is a fixed version in the
Enhancements Pack.
There is also the following unfixed bug: Some situations (eg. 3-byte
instruction at $1FE..$200 when range
argument was "0100FF") result in the mini-disassembler not detecting the
end of the range and instead wrapping back around.
Music:
Monotonic musical notes are generated by pulsing the flag output at
suitable rates, with the program "reading" the music from a section of
memory. The timing of the music is determined by a time value called
"UNIT", which is an even number of up to 15 bits, such that $5160 is about
1/32 of a second.
Each note is specified by two bytes. The first byte represents the
number of UNITs that the note will last: $01 gives a duration of 1 UNIT,
while $00 gives 256 UNITs, or 8 seconds with a UNIT value of $5160.
The second byte is split into three fields. The most significant bit,
bit 7, indicates either a note (%0) or a rest (%1). The next three bits,
bits 4, 5 and 6, specify the octave. %111 represents the top octave, while
%000 represents the lowest. In practice, the three lowest octaves are not
usable, giving a range of only five octaves.
The remaining four bits in the second byte represent the note within the
octave. The first note in any octave is E, represented by $0, while the
last note is D# (D sharp), represented by $B.
For rests, bits 6 to 0 are not used, so all rests become $80.
It is best to start and end all programs (tunes!) with $80 $80, a long
rest, to separate the music from the noises PIPBUG makes while
communicating with the terminal. To signify the end of a tune, insert $02
$FF after the long rest.
"Yankee Doodle" occupies locations $5D4 to $6B7, and requires a unit
value of $2800, while "Bach" occupies locations $6B8 to $7A3, and requires
a unit value of $7000.
To run the program, type:
G58C [<address of first note>] [<value of UNIT>] <CR>
G58C 5D4 2800<CR>
G58C 6B8 7000<CR> "
Note
Very low
Low
Middle
High
Very high
E
$30
$40
$50
$60
$70
F
$31
$41
$51
$61
$71
F#/Gb
$32
$42
$52
$62
$72
G
$33
$43
$53
$63
$73
G#/Ab
$34
$44
$54
$64
$74
A
$35
$45
$55
$65
$75
A#/Bb
$36
$46
$56
$66
$76
B
$37
$47
$57
$67
$77
C
$38
$48
$58
$68
$78
C#/Db
$39
$49
$59
$69
$79
D
$3A
$4A
$5A
$6A
$7A
D#/Eb
$3B
$4B
$5B
$6B
$7B
Rest
$80
$80
$80
$80
$80
Note that there is a short delay for Yankee Doodle, and a long delay for
Bach, before they actually begin to play the song.
Nim:
The winning strategy is as follows:
You will have a turn where there are 6..8 widgets. Taking 1..3 widgets
accordingly on this turn will leave 5 widgets.
The computer must then take 1..3 widgets, leaving 2..4 widgets.
You should then take 1..3 widgets accordingly, to leave 1 widget and
therefore win.
Ie.:
If 23 remaining on your turn, take 2 leaving 21.
If 22 remaining on your turn, take 1 leaving 21.
If 21 remaining on your turn, take 3 leaving 18 but you are in danger.
If 20 remaining on your turn, take 3 leaving 17.
If 19 remaining on your turn, take 2 leaving 17.
If 18 remaining on your turn, take 1 leaving 17.
If 17 remaining on your turn, take 3 leaving 14 but you are in danger.
If 16 remaining on your turn, take 3 leaving 13.
If 15 remaining on your turn, take 2 leaving 13.
If 14 remaining on your turn, take 1 leaving 13.
If 13 remaining on your turn, take 3 leaving 10 but you are in danger.
If 12 remaining on your turn, take 3 leaving 9.
If 11 remaining on your turn, take 2 leaving 9.
If 10 remaining on your turn, take 1 leaving 9.
If 9 remaining on your turn, you will eventually lose.
If 8 remaining on your turn, take 3 leaving 5.
If 7 remaining on your turn, take 2 leaving 5.
If 6 remaining on your turn, take 1 leaving 5.
If 5 remaining on your turn, you will soon lose.
If 4 remaining on your turn, take 3 leaving 1 and winning.
If 3 remaining on your turn, take 2 leaving 1 and winning.
If 2 remaining on your turn, take 1 leaving 1 and winning.
If 1 remaining on your turn, you have already lost.
Number Game:
Numbers up to 65535 are possible.
The target number is stored at $486..$487 in little-endian format.
The number of turns taken is stored at $4A8.
On Screen Clock:
*($573) = tens of hours
r3 = ones of hours
r2 = tens of minutes
r1 = ones of minutes
All values are stored in ASCII format. Eg. for '5', use $35 (ASCII '5'),
not $05.
Eg. use this sequence of debugger commands for 11:58:
P
E $573 '1'
E R3 '1'
E R2 '5'
E R1 '8'
J $500
P
Othello (Reversi) 2.0:
Printer Routines, Trace Routine:
Reaction Timer:
Relative Branch Calculator:
Enter destination address (4 hex digits), then "=" appears, and tells you
the relative offset (or "?" if out of range).
The first digit of each pair entered is not echoed to the display until the
second digit has been input.
Rotate:
A B C D
E F G H
I J K L
M N O P
If a mistake is made, it can be corrected once between valid rotations.
Any two adjacent letters can be exchanged, with the proviso that only one
exchange is permitted. When the required pattern has been achieved, or
when the game is aborted, the program will print out the number of moves
used.
The program occupies locations $440 to $5C7, and uses routines from
PIPBUG. To run the program, type:
G440<CR>
Here is a sample printout. The "Z" command was used to terminate the
game.
*G440
EPLI
BFHK
CNAG
EPLI
BNFK
CAHG
EFLI
BANK
CHFG
EPLI
BAFN
CHGK
EPLI
BAGF
CHKN
EPMI
BAGF
CHKN
EAPI
BGMF
CHKN
EAPI
BGKM
CHNF
EAPI
GMNF
CHKN
EAPI
BHGF
CKMN
If you wish to exchange two adjacent letters, type X. The program will
respond with "EXCHANGE:", and expect you to type in the two desired
letters. If you cannot solve a particular pattern, type Z, and this will
abort the game.
An average pattern, with only one exchange permitted, should take
between 25 and 30 moves. Early attempts may take more."
Note that the game does not enforce the rule about only permitting one
exchange per game.
The unpatched version (ie. as found in the Games Pack) will not work on
Ami/WinArcadia. You should use the patched version (ie. as found in the
Enhancements Pack).
RYTMON:
Solitaire:
Star Shoot:
No.
Start
End
123
...
***
456
.*.
*.*
789
...
***
1
2
3
4
5
6
7
8
9
.!-
!!-
---
!.!
---
---
-!.
-!!
---
!--
.--
!--
-!-
!.!
-!-
--!
--.
--!
---
!!-
.!-
---
---
!.!
---
-!!
-!.
! means the star or dot becomes a dot or star (respectively).
- are unchanged.
It is possible to reach a configuration with zero stars and thus no
possible moves, losing the game.
Time:
The two most likely possibilities would be:
(a) the program was not originally tested and tuned to a sufficient
precision by its programmer; and/or
(b) the real machine is spending a certain number of cycles servicing
interrupts (which don't occur in the emulator).
Of course, since it starts counting from minute 1 rather than minute 0,
the time as shown in this program will be minute later than that shown by
the emulator.
When this program says "0100" (ie. "one hour"), emulator time should be
approximately "00:59:00.00" (though it would be fair to allow a few
milliseconds for initialization). However, emulator time when this event
occurs is actually only "00:58:47.20". So this program is 12.80 seconds
fast over that 59 minutes. (Or, conversely, you could suggest that the
emulator is slow by that amount, or a combination of both.)
Such accuracy is approximately 1:276.5625 (slightly worse than 1 second
fast per 5 minutes), which makes this program rather useless over lengthy
periods.
Vector Magnetometer:

Signetics Instructor 50
The start address for user programs can be specified at runtime by the
user as with eg. the Elektor TV Games Computer.
BIOS calls are made via
eg. ZBSR *DISPLY; there is a zero page jump table at $1FE6..$1FFF.
Region
Size
Basic version
Expanded version
$0000..$01FF
512 bytes
user RAM
user RAM
$0200..$0FFE
3582 bytes
unused
expansion RAM
$0FFF
1 byte
I/O port
I/O port
$1000..$177F
1920 bytes
unused
unused
$1780..$17BF
64 bytes
user RAM
user RAM
$17C0..$17FF
64 bytes
monitor RAM
monitor RAM
$1800..$1FFF
2K
monitor ROM
monitor ROM
$2000..$7FFF
24K
unused
expansion RAM

I/O Devices
The 28-key keyboard is as follows:
------Left Keypad------ ---------Right Keypad----------
.SENS.. .WCAS.. .BKPT.. ...C... ...D... ...E... ...F...
..INT.. .RCAS.. ..REG.. ...8... ...9... ...A... ...B...
..MON.. .STEP.. ..MEM.. ...4... ...5... ...6... ...7...
..RST.. ..RUN.. ENT NXT ...0... ...1... ...2... ...3...
8-digit 8-segment LED display (red on black):
"PARALLEL I/O" section, consisting of:
8 glow LEDs ("7".."0");
8 corresponding toggle switches (unlabelled);
Toggle switch with 3 possible positions
(up, middle and down, corresponding to "MEMORY $0FFF", "EXTENDED I/O PORT $07"
and "NON-EXT DATA PORT", respectively).
"The default is probably EXTENDED I/O PORT $07."
WRTD,rn to write to the glow LEDs
WRTE,rn $07 to write to the glow LEDs
STRA,rn $0FFF to write to the glow LEDs
"RUN" glow LED:
"FLAG" glow LED, showing the state of the Flag pin of the CPU.
"INTERRUPT" toggle switch: "DIRECT" or "INDIRECT":
"INTERRUPT SELECTOR" jumper (on underside of machine):
"KEYBOARD" (ie. INT key).
"The default is probably keyboard."
S-100 bus (at rear) (not emulated).
"CASSETTE" jacks: "PHONE" and "MIC":
As with the Elektor, the rate at which bits (and thus bytes) can be
loaded/saved depends the actual data payload (ie. depends on whether they
are "0"s or "1"s).
Port $F8 bit 4 is FREQ. The BIOS is flipping that at a constant regular
rate (at least while recording).
Port $F8 bit 3 is ENV. That is high whilever we are actually recording a
bit, and goes low between bits. It stays high for longer for a "0" bit
than for a "1" bit.
So whilever ENV is high, we just write the current status of the FREQ bit
to the tape, and whilever ENV is low, we just write silence.
It gets NANDed, so if ENV and FREQ are both high, we are low, and
otherwise, we are high.
It sets port $F8 to $10 and $18 while writing, and $00 at rest.
During playback, the Sense bit is set directly from the tape
based on whether above or below the zero-crossing point.

USE BIOS
Error 2 means: "Restricted command."
Error 9 means: "Next instruction is in the MONITOR area."
Ie. if the STEP button is pressed and the next instruction would be in
the monitor area, it will be reported by the appearance of Error 9.
R1..R2: Pointer to byte preceding string.
R3: $00/$01/$80. $01 returns immediately.
The USE BIOS only allows character-level (ie. glyph-level) access. The
character set is as follows:
$00
$01
$02
$03
$04
$05
$06
$07
$08
$09
$0A
$0B
$0C
$0D
$0E
$0F
$10
$11
$12
$13
$14
$15
$16
$17
$18
$19
$1A
$1B
$1C
0 or O
1 or I
2
3
4
5
6
7
8
9
A
b.
C
d.
E
F
P
L
U
r
H
o
=
space
J
-
.
Y
n
### ..# ### ### #.# ### ### ### ### ### ### #.. ### ..# ### ### ### #.. #.# ... #.# ... ... ... ..# ... ... #.# ...
# # . # . # . # # # # . # . . # # # # # # # # . # . . # # . # . # # # . # # . . # # . . . . . . . # . . . . # # . .
#.# ..# ### ### ### ### ### ..# ### ### ### ### #.. ### ### ### ### #.. #.# ### ### ### ### ... ..# ### ... ### ###
# # . # # . . # . # . # # # . # # # . # # # # # # . # # # . # . # . # . # # # . # # # # . . . . . # . . . . . # # #
### ..# ### ### ..# ### ### ..# ### ..# #.# ### # ### ### # ### #.. #.. ### ### #.. #.# ### ### ... ### ... ... # ### #.#
Available letters: ABCDEFGHIJLNOPRSUY
Unavailable letters: KMQTVWXZ

Game Help

Event
Odds
0 lamps lit
250:1
1 lamp lit
15:1
2 lamps lit
7:1
3 lamps lit
7:2 (3.5:1)
4 lamps lit
5:2 (2.5:1)
5 lamps lit
7:2 (3.5:1)
6 lamps lit
7:1
7 lamps lit
15:1
8 lamps lit
250:1
0..1 lamps lit
25:1
2..3 lamps lit
2:1
4..5 lamps lit
1:1
6..8 lamps lit
6:1
0..2 lamps lit
11:2 (5.5:1)
3..5 lamps lit
2:5 (1:10)
6..8 lamps lit
11:2 (5.5:1)
Specific 2-digit number
250:1
Specific MS digit
15:1
Specific LS digit
15:1
Any one of 5 specified 2-digit numbers
50:1
Any one of 10 specified 2-digit numbers
25:1