11

The POKEY module was used in many, many Atari arcade games, including most that contained the Atari Math Box. It could be used to sample potentiometers, scan matrices of switches and, more famously, to generate distinctive tones, tunes and sound effects that the 6502 could not.

What API did the POKEY module provide to allow it to be programmed from the main processor?

12

The POKEY module has a random number generator, six scan lines, eight potentiometer ports, three timers, a serial port and four audio channels.[2#1]

Hardware

The POKEY chip (C012294 (original), C012294-02 (dual-core) and C012294-04 (quad-core))[1§2] have 40 lines. These are:

  • Pin 1: Vss: Ground[1§3] at 0V.
  • Pins 2 - 6: D3, D4, D5, D6, D7: Data Bus I/O.[1§3]
  • Pin 7: Ø2: Phase 2 Clock Input.[1§3]
  • Pin 8 - 15: P6, P7, P4, P5, P2, P3, P0, P1: Potentiometer Scan.[1§3]
  • Pin 16: KR2: Keyboard Row strobe Input.[1§3]
  • Pin 17: Vcc: Power at 5V.[1§3]
  • Pin 18 - 23: K5, K4, K3, K2, K1, K0: Keyboard Scan Output
  • Pin 24: SID: Serial Input Data.[1§3]
  • Pin 25: KR1: Keyboard Row strobe Input.[1§3]
  • Pin 26: BCLK: Bi-directional Clock I/O.[1§3]
  • Pin 27: ACLK: Serial Clock Output.[1§3]
  • Pin 28: SOD: Serial Output Data.[1§3]
  • Pin 29: IRQ: Interrupt Request Output.[1§3]
  • Pin 30 - 31: CS0, CS1: Chip Select.[1§3]
  • Pin 32: R/W: Read / Write I/O Control.[1§3]
  • Pin 33 - 36: A3, A2, A1, A0: Memory Address Input.[1§3]
  • Pin 37: AUD: Audio Output.[1§3]
  • Pin 38 - 40: D0, D1, D2: Data Bus I/O.[1§3]

Software

Registers

The POKEY chip was accessible as a memory-mapped device. On Atari 8-bit computers it is mapped to the D2xx page,[1§4] and on the Atari 5200 it is mapped to the E8xx page.[1§4]. There are 29 registers,[1§4] each with a different function depending on whether it was read from or written to.[1§4] These are:

  • Read 00 - 07: POT0 - POT7:[1§4]
    The "POT" (potentiometer) registers map to analog-to-digital converter ports.[1§6]
  • Write 00 - 07: (AUDF1, AUDC1) - (AUDF4, AUDC4):[1§4]
    The AUDFx registers are for controlling audio frequency, containing the interval (in clock cycles) between successive cycles as an 8-bit integer from 1 to 256.[1§5.1]
    The AUDCx registers are for controlling distortion and volume, or for playing PCM audio streams.[1§5.2] The bit-field is interpreted as follows:
    • Bits 0 - 3: Volume:
      A four bit integer representing the volume of the channel,[1§5.2], presumably used as a multiplicative factor from 0 to 15. TODO: Test volume behaviour precisely.
    • Bit 4: Volume only?: A boolean flag that determines the use of the Volume value.[1§5.2] If this flag is 0, the Volume value will be used to modify the amplitude of the channel's waveform. If this flag is 1, the Volume value will be used as the channel output,[1§5.2] which can be used to play PCM audio[1§5.2] at a sample rate limited by the speed at which the register is updated.TODO: Can this be tested?
    • Bit 5 - 8: Noise: Settings for noise and distortion. According to Wikipedia, the settings are interpreted as follows:TODO: Is this correct? Test +> A0 & E0
      | Noise Value | Bits Value |          Description          |
      | ----------- | ---------- | ----------------------------- |
      |    0 0 0    |    $00     | 5-bit then 17-bit polynomials |
      |    0 0 1    |    $20     | 5-bit poly only               |
      |    0 1 0    |    $40     | 5-bit then 4-bit polys        |
      |    0 1 1    |    $60     | 5-bit poly only               |
      |    1 0 0    |    $80     | 17-bit poly only              |
      |    1 0 1    |    $A0     | no poly (pure tone)           |
      |    1 1 0    |    $C0     | 4-bit poly only               |
      |    1 1 1    |    $E0     | no poly (pure tone)           |
      
  • Read 08: ALLPOT:[1§4] A bit-field containing one bit per port. On POTGO, all bits are set to 1; they are individually set to 0 when scanning is complete and their registers are ready to be read.[1§6.9]
  • Write 08: AUDCTL:[1§4]
    A bit-field containing flags corresponding to the behaviour of the audio channels. The bit-field is interpreted as followed:
    • 0: Clock Base rate[2#2.2] / Frequency Divider rate:[1§5.3]
      Determines the base clock speed for the audio channels. A value of 0 means 64kHz,[2#2.2][1§5.3] and a value of 1 means 15kHz.[2#2.2][1§5.3]
    • 1: High pass filter, channels 2 and 4?:[2#2.2][1§5.3]
      If 1, filters channel 2 based on base frequency of channel 4,[2#2.2] only allowing through frequencies higher than specified.[1§5.3] As explained by the Atari Pokey Data Sheet:

      The high-pass filter consists of a D-type flip-flop and an exclusive-OR gate. The noise control circuit output is sampled by this flip flop at a rate set by the "high-pass" clock. The input and output of the flip-flop pass through the exclusive-OR gate. However, if it is lower than the clock rate, the flip-flop output will tend to follow the input and the two exclusive-OR gate inputs will mostly be identical (11 or 00) giving very little output. This gives the effect of a crude high-pass filter, passing only noise whose minimum frequency is set by the high-pass clock rate. Only channels 1 and 2 have such a high-pass filter. The high-pass clock for channel 1 comes from the channel 3 divider. The high-pass clock for channel 2 comes from the channel 4 divider.

    • 2: High pass filter, channels 1 and 3?:[2#2.2][1§5.3]
      If 1, filters channel 1 based on base frequency of channel 3,[2#2.2] only allowing through frequencies higher than specified.[1§5.3] See above for a detailed description of the behaviour.
    • 3: Connect channels 3 & 4?:[1§5.3]
      If 1, use channel 3 as channel 4's clock;[2#2.2] creates 16-bit channel.[1§5.3] TODO: The base of channel 3 or the signal?
    • 4: Connect channels 1 & 2?:[1§5.3]
      If 1, use channel 1 as channel 2's clock;[2#2.2] creates 16-bit channel.[1§5.3]
    • 5: Channel 3 clock[2#2.2] frequency:[1§5.3]
      TODO: 1§5.3 & 2#2.2 contradict; test.
    • 6: Channel 3 clock[2#2.2] frequency:[1§5.3]
      TODO: Ditto
    • 7: 17-bit / 9-bit poly?:[2#2.2][1§5.3]
      Determines whether the internal 17-bit polynomial register is read as 9-bit.[2#2.2] If this flag is 0, the register is read as 17-bit; if it is 1 the register is read as 9-bit.[1§5.3]

Interrupts

There are eight interrupts,[1§8] numbered 0 to 7.[2#8] These are:

Interrupts are managed using the IRQEN register and read using IRQST.[2#8] To enable an interrupt, set the relevant bit of IRQEN to 1; to disable it set the bit to 0.[2#8] This register isn't initialised by default; this must be done before enabling processor IRQ to avoid undesired behaviour.[2#8] The IRQST register is initially full of 1 bits, and goes to 0 when the relevant interrupt is fired.[2#8] In order to reset a given bit of IRQST, the relevant bit of IRQEN must be (temporarily) set to 0.[2#8] Note that this does not apply to bit 3 (XD); this bit of IRQST will be 0 when serial output is empty and 1 when it is not regardless of whether bit 3 of IRQEN is reset.

  • 1
    This doesn't actually explain what the API is. I think a useful answer would explain how you write code that uses POKEY; it would be rather difficult to do so based on this answer... – Stephen Kitt Dec 19 '16 at 15:20
  • @StephenKitt Should I add the part about the memory registers to the answer? I thought it would be better to post now than to add more information, so omitted it. – wizzwizz4 Dec 19 '16 at 15:25
  • 2
    Yes, that's the most interesting part if you're actually trying to use POKEY, and it's really what defines the API — you could replace POKEY with some other hardware, as long as it provided the same registers in some way (and the same interrupts). To really make your answer useful you should try to write code which uses POKEY and transcribe what you had to find out in order to get it working ;-). – Stephen Kitt Dec 19 '16 at 15:45
  • You can use an Atari 8-bit emulator to test your code. – Stephen Kitt Dec 19 '16 at 16:14
  • The API is using instructions that read and write memory to program the chip and do what you want. All 6502 based systems memory-mapped I/O devices into the 64K address space and were spoken to as though they were RAM. I don't believe the Atari BIOS or ROM provided any API routines. – LawrenceC Apr 7 '17 at 14:53

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.