Content-type: text/plain; encoding=utf-8
Date: Sat, 18 Aug 2018 09:59:51 +0000
<<JKOK234F>> HYDRATRON (JKZ90H9K)
The Most User-Hostile POKEY Sequencer for The Atari Home Computer
"It's as easy as programming in raw machine code!"
The HYDRATRON is a ...well, what the hell is it? You could say that it's a music tracker/sequencer*. It can certainly be used that way. It might be better thought-of as a live coding environment for music/sound.
* When I first started working on it, I thought of it as a "chain sequencer", meaning a sequencer in which multiple simultaneous sequences of varying lengths are chained together via GOTO-like statements. Very quickly I started thinking that it would be even better if I could write little music programs, not just scores.
In its current incarnation, the HYDRATRON provides you with little more than a hex editor that you use to manipulate the contents of the computer's memory** whilst an interpreter runs in the background and executes the program code that you're plugging into RAM.
** Yes, you can scroll up to a page of memory with OS code in it and promptly crash the computer if you want to.
The HYDRATRON is programmed with a sort-of virtual machine code; the virtual machine works like this:
There are four "heads", each with a program counter, delay counter, and a single general-purpose register. At every tick of the time-clock they decrement their delay counter, and when the counter reaches zero they execute the instruction pointed-at by their program counter. The instructions are all four bytes long, and look like this:
[DELAY] [OPCODE] [OPERAND1] [OPERAND2]
The DELAY byte sets the head's delay counter. After the current instruction is performed, the head will wait this number of "ticks" (jiffies, 60ths of a second – or 50ths, depending on where you live) before executing the next instruction.
The OPCODE byte tells the head what to do; maybe change the pitch or timbre of a POKEY channel, change the program counter of a head, store bytes in the head's register, &c..
And of course the OPERAND bytes provide data needed to execute the instruction.
[I have prepared a short animation illustrating the operation of the LSEQ machine. It should be inlined here.]
At the time of this writing, HYDRATRON has the the following instruction set:
00 - RETPAGE - Return head to the beginning of the current memory page
01 - SETF1 - Set AUDF1
02 - SETF2 - Set AUDF2
03 - SETF3 - Set AUDF3
04 - SETF4 - Set AUDF4
05 - SETC1 - Set AUDC1
06 - SETC2 - Set AUDC2
07 - SETC3 - Set AUDC3
08 - SETC4 - Set AUDC4
09 - SETCTL - Set AUDCTL
0A - EORCTL - Perform Exclusive OR with AUDCTL
0B - JUMPTO - JMP current head to address
0C - STOR - Store a value in the current head's register
0D - MAC - Jump head to macro/sub-sequence
0E - MACRET - Return from macro/sub-sequence
0F - OPNOP - Do Nothing!
10 - STOP - Stop/disable the current head
11 - MODF1 - Add value to AUDF1
12 - MODF2 - Add value to AUDF2
13 - MODF3 - Add value to AUDF3
14 - MODF4 - Add value to AUDF4
15 - SETF1R - Set AUDF1 from register
16 - SETF2R - Set AUDF2 from register
17 - SETF3R - Set AUDF3 from register
18 - SETF4R - Set AUDF4 from register
19 - SETC1R - Set AUDC1 from register
1A - SETC2R - Set AUDC2 from register
1B - SETC3R - Set AUDC3 from register
1C - SETC4R - Set AUDC4 from register
1D - SETCTLR - Set AUDCTL from register
1E - MODR - Modify register value
1F - HOPNE - HOP over next op if register does Not Equal the passed value
20 - JMPONZ - Jump head to passed address if register equals Zero
21 - GOHED1 - Move head 1 to new page and GO!
22 - GOHED2 - Move head 2 to new page and GO!
23 - GOHED3 - Move head 3 to new page and GO!
24 - GOHED4 - Move head 4 to new page and GO!
3C - PEEK - Load a byte of memory into the head's register (sets register high byte to 0)
3D - PEEKW - Load a word of memory into the head's register
3E - POKE - Set a byte of memory
3F - POKEW - Set a word of memory
This instruction set is by no means final. Aside from some renaming, there are several instructions I would like to add, and some instructions that I may remove (the SETFx and SETFxR instructions for example could easily be combined).
As powerful as programs like Theta Music Composer are, they're not performance sequencers; the sequences and instruments cannot be edited as they play. Moreover, chip trackers are designed for the composition of pop/dance music, not for weirdo, free-form, avant-garde-y arty music. I wanted something that would allow me to playback and modify sequences and sounds in real time, the way that one can with step sequencers and modular synthesizers, and I wanted to be able to compose way outside the box of Western musical traditions and into the realm of generative/stochastic music.
OKAY, BUT WHY IS THE INTERFACE SO BAD?
The interface is really user-hostile, I know. The reason is simply that I didn't want to spend a lot of time writing a UI; my priority right now is experimenting and developing the instruction set. Once I've developed the back-end to a place I'm happier with, then I would like to build a nice UI around that.
For the time being, if punching hexadecimal digits into a grid ain't your idea of a good time, there is another way to do it: you can write HYDRATRON programs in a text editor and assemble them into the program with ATasm. Check the comments in the sequence.m65 file for the details. It's not very elegant at the moment. In the future I'd like to write a little tool that will convert a clean, plain-text format into the ATasm code for assembly.
- Better UI
- Save state to disk
- More heads!
- Tool for writing plain-text programs
- Dual POKEY?
<<JL2U6T9W>> Hydratron rename (JLOQRZD1)
Ugh. Hydratron was a terrible, hasty name choice. LSEQ, the original hasty name choice, however inaccurate, looks/sounds better.
Better still: P·HYDRA
Now that the darned thing has six heads, I feel okay calling it hydra-something, and P·HYDRA has a nice ring to it. I've sat on it for a few days and I think we'll go with that.