Encoding Software in Barcodes, the Eight-Bit Magazine Way
On RetrBattlestations one of the most popular challenges is a recreation of the days when magazines used to publish their own programs. Back before the internet, and when dialup was still expensive, magazines would publish source code listings and the only way to get it into your computer was to type it in.
Whenever I work on one of these challenges I come up with a BASIC program for people to type in on their computers. But I always think about how some magazines had also started publishing machine readable versions of the programs in the form of barcodes. The barcodes were in a proprietary format that required special hardware to read in. The format was called "Softstrip" and was invented by a company named Cauzin.
A couple of years ago during one of the BASIC challenges I checked on eBay and was able to get two Cauzin Softstrip readers for about $40. They were complete with the power supplies and each included the kit with the floppy, manual, and cables for connecting to a PC. Only one of the readers works so I'm glad I got both of them. (The reader seems to be actually glued shut, so I'm not sure if it can be repaired.)
During the BASIC challenge this year I got into a discussion on Twitter with a few people about hardware we were sure we'd have working by the next BASIC challenge and I mentioned the Cauzin Softstrip and how I had no software for creating the barcodes. Of course I did some more googling to see if there was anything new out there since the last hundred times I had tried. There was! A manual for a program called "Stripper" for the Apple II had been scanned in containing the software as Softstrip barcodes. Of course trying to print out the pages and read them back in on the Cauzin reader didn't work. But @ty2010b found that there was a disk image with the software already read in so I didn't have to try to repair the bad images in the PDF!
Being able to print barcodes out from the Apple II seemed like a good start, but it wasn't what I really wanted to do. The software was made to only print on either an Epson FX-80 or an Apple ImageWriter since the escape codes were hard coded in. There was no way to create an image and save it. It was also limited to only printing low density Softstrips. And it was written to only work under DOS 3.3, making transferring files to it a hassle.
My first thought was that since I at least had software I could reverse engineer it to figure out the algorithm. I ended up writing a custom disassembler that could track jumps and add some labels. There were some very bizarre calling conventions used where arguments to a subroutine were placed in the bytes right after the JSR and the called subroutine would alter the stack so that the return would skip over them. The assembly was far too difficult to make much sense of since it spent 99% of its time just shuffling pointers to pointers in and out of the zero page. The assembly is definitely not hand coded and is the output from some compiler. I don't know what language or compiler was used, but it was a crummy one.
If you're interested, here's the disassembly of the Epson FX-80 version of the program.
The manual that contained the Cauzin Stripper program also described how bits are encoded, although it didn't include all the details on how the barcode is organized. On archive.org there's also a document that talks about how to control the reader and describes the data that it outputs, but again doesn't get into how the barcode is structured. And there's also a patent document which includes a few more details about the layout of the barcode, but not how the actual data itself is arranged. But I hoped that with all three as a reference I might be able to figure everything out.
After spending several days decoding existing barcodes by hand and constantly reviewing the sparse documentation I had, I started to work out what all the different pieces were. I cobbled together a program to create a barcode as a bitmap and then imported the bitmap into Illustrator to distort it to the correct dimensions. I printed it out and had the reader try it, and it almost worked! It would read the entire strip but then complain that the data was bad. It turned out that I was calculating the one byte checksum incorrectly. Once I solved that I was able to create my own Softstrip barcode and read it back in successfully!
The Missing Bits
Cauzin uses something called a "dibit" to encode bits. It essentially uses two bits to encode a single bit. A dark square followed by a light square represents a zero, a light square followed by a dark represents a one, and the other two patterns are considered invalid and an error. Not exactly an efficient coding system.
On the left side of the barcode is the checkerboard (32) and the right side has the zipper (36). The reader uses those to maintain sync while scanning down the barcode.
Complete 8 bit bytes are encoded in a strip, however the encoding is based around nibbles. The density of a barcode is determined by how many nibbles wide it is. The top of a barcode contains the "horizontal sync" pattern (20) which tells the reader how many nibbles are used. The minimum is 4 nibbles, and the maximum is 12 based on the smallest dot size that the reader can see. For each additional nibble after the minimum of four, another stripe is added next to the wide block, with the stripes being mirrored. In this example the strip is 8 nibbles wide.
Below the horizontal sync is the vertical sync (18). This is just a bunch of 0x80 bytes properly encoded with parity with the same data repeated over and over to make sure there at least 4mm of rows.
Parity bits are the first and last bits. Parity is calculated from every other even bit (0, 2, 4, 6, etc.) and put on the left, and every other odd bit (1, 3, 5, 7, etc.) is on the right.
When reading the vertical sync strip is eaten by the reader, along with the first three 0x00 bytes at the beginning of the strip. The reader uses the 4th and 5th bytes to determine the number of bytes encoded in the entire strip and then sends all the data to the computer. If there are any parity errors those lines will be skipped and not sent to the computer, but it will also not count them as part of the strip and so when it reaches the end it will send an error code to the computer. If it sees any illegal dibit patterns the reader will abort immediately.
I've put my barcode creation program up on github. It's still a little crude right now and doesn't support splitting files into multiple strips or outputting PDF. But it is good enough for making test barcodes. If there's enough demand I may work on the program and make it a little more complate and add more features.