Archives

My clear acrylic laser-cut case design for Floppy Emu looks sharp, but doesn’t match the visual style of classic Apple II or Macintosh systems. It’s also a bit tedious to assemble. A few people have suggested a Floppy Emu case that looks more like a retro 3.5 or 5.25 inch Apple drive, with Apple design details and a beige/white color. In that spirit, my friend Allan recently did some experiments with a 3D printed white case for the Floppy Emu, and the results look promising.

3D printing has the advantage of making any shape possible, instead of being constrained to interlocking 2D pieces with laser cutting. This enables the case to be built as just two pieces, rather than the six pieces needed for the laser-cut version. It also enables the button plungers to be built directly into the top plate, so they can’t fall out, making the whole thing easy to assemble. If you’ve struggled with the button plungers in the laser cut case, then you’ll appreciate this.

With 3D printing, it’s also possible to approach the appearance of a retro computer accessory. The case can be matte white, instead of glossy acrylic. 3D grooves and other small details can be modeled directly into the case, instead of being limited to 2D etching. Nobody will confuse it with a 1984 Apple peripheral, but at least it will be a lot closer.

I’ve mostly avoided 3D printing until now, because I’ve found it to be slow, expensive, and imprecise. Each one of these test prints required many hours of printer time and baby-sitting. The large time sink wouldn’t an issue if I used a commercial 3D printing service instead of home printing, but initial estimates are that a 3D printed case would cost perhaps 3x as much to manufacture as the current laser-cut case design. Maybe that would still be OK if the improved appearance and ease of assembly made it worth the extra cost to customers, but it’s a lot to ask.

Imprecision has been my biggest concern with 3D printing. Using my own budget printer, it seems half the prints I make come out badly deformed. Even the “good” prints always have a smooshed corner or deformed detail or other minor problem. It’s not terrible if you’re making a prototype for self-use, but I’m not sure it would be acceptable if making hundreds of them for sale to customers. Allan’s first case experiments showed some of the same types of deformities, although he was able to improve it somewhat in later iterations by making adjustments to his printer settings. Here’s an example of what I’m talking about:

Note how some of the grooves at left aren’t clean and even, and there’s a diagonal texturing across the whole surface that’s visible in some areas but not others. It’s hard to see in the photo, but the text and icons also have a slightly uneven appearance.

What surprised me was a test print made in Allan’s friend’s high-end 3D printer: it’s much more professional-looking, with very consistent print appearance across the whole case. That’s the print you see in the title photo above. I don’t know exactly what model of printer it was, or the cost, but I’ll try to find out. Here’s a close-up of the case from the better 3D printer, for comparison (click the image to see a high-resolution version).

A question to readers: would a 3D printed “retro-style” Floppy Emu case interest you? What features do you think would be most important? What do you think would be a fair price for something like this?

The human body is electrically conductive. A piece of fruit will also conduct electricity, as will basically anything else that’s organic. We can leverage this fact to create a fun little afternoon project: a digital fruit piano. No soldering is necessary, and the whole thing takes less than an hour, even for a total beginner like my 9-year-old daughter. What sound does a banana make? Let’s fine out.

While humans and fruit do conduct electricity, they’re pretty bad at it. Both typically have an electrical resistance that’s in the 1-megaohm range, depending on how moist your skin or nectarine is. This design uses your body and the fruit as part of the circuit, flowing current through the human-fruit “wire”, but the high resistance means that the currents involved are tiny. The piano player isn’t going to feel a shock, or even feel anything at all. She’ll just lightly touch different bits of fruit to play a song, almost as if by magic.

This isn’t my original design. The idea of controlling a digital device by using the human body as part of the circuit has been around for quite a while, and the Makey Makey has popularized it with a nice little kit. If you like this type of project, definitely check out the Makey Makey! But if you’re lazy and cheap like me, you can build a similar device yourself with only an Arduino and some hookup wire, a few resistors, an audio speaker, and a selection of bananas, pears, and peaches.

How does it Work?

The basic concept is simple. Each piano key is a voltage divider circuit involving two resistors: one 1-megaohm resistor and one piece of fruit. Touching the fruit will change the resistance in the circuit, resulting in a change to the voltage at the junction between the two resistors. The Arduino can measure this changing voltage with an analog input, and use it to control an audio speaker.

To complete the circuit, one hand should be connected to the Arduino’s ground pin, while the other touches the fruit. Current will flow through one hand, up the arm, across the chest, down the other arm, and back to Arduino GND. For convenience’s sake I connected GND to a metal ruler, but a plain jumper wire also works fine. For the fruit connection, just stab a wire straight into the fruit. Soldering a banana works poorly…

If the hand isn’t touching the fruit, then the whole fruit-hand-body section becomes an open circuit with infinite resistance. In this case, the circuit simplifies to just +5V connected through a 1 meg resistor to the analog input. Because the analog input draws virtually zero current by itself, there will be no current flowing in the circuit and no voltage drop across the 1 meg resistor (remember Ohm’s law V = iR, so when i = 0 then V = 0). The voltage measured at the analog input will still be +5V, and Arduino’s analogRead(A0) function will return 1023, the maximum possible value for its 10-bit resolution.

When the hand touches the fruit, the fruit-hand-body section forms an organic resistor of about 1 megaohm. Current will flow from +5V through the real 1 megaohm resistor, then through the fruit-hand-body 1 megaohm resistor and down to ground. The total resistance between +5V and GND is 2 megaohms, and with two equal value resistors, the voltage at the point midway between them will be half the total voltage drop. That means the Arduino’s analog input will see 2.5V, and the analogRead(A0) function will return a value around 512.

To make a piano, a simple Arduino program is needed to continuously poll each analog input, and play a tone if the analog value is below an appropriate threshold. I used a threshold of 800, but you’ll need to experiment to find the value that works best for you. The sample program uses tone frequencies corresponding to the notes CDEFGA of a C major scale, making it easy to bang out favorites like Mary Has a Little Lamb, Hot Cross Buns, and I Ate the G Key.

Each of the six fruits is connected to one of the six Arduino analog inputs A0 to A5. If you’re wiring this up at home, duplicate the pictured banana circuit six times, connecting the first to A0, the second to A1, and so on up to A5. Then connect your speaker’s black wire to GND and red wire to Arduino pin 8. Happy fruit playing!

Vintage Computer Festival West XI is happening next weekend, August 6-7 at the Computer History Museum in Mountain View, California. I’m belatedly dusting off the hardware for my exhibit and preparing the demos and signage. Anybody have a trade show style backdrop they’d like to lend me?

I’ll be exhibiting three of my hand-made computer creations, each of which has gone through some modifications for the show:

BMOW 1 – My original custom-made CPU and computer that kicked off this blog and my journey into hobby electronics. BMOW 1 is an 8-bit CPU, implemented with 7400-series TTL discrete logic and a few PALs. Built around this is peripheral hardware for I/O, sound, and video. The end result is a custom creation that’s vaguely similar to an Apple II in its performance and capabilities. And it’s all hand wire-wrapped, with thousands of individual wires.

New for VCF West, I’ve cut a porthole in the bottom of the case and added interior case lighting, to showcase the glorious mess of wires inside. I was nervous I’d break something while removing and replacing all the parts in the case, but BMOW survived and is still running strong.

68 Katy – A 68000-powered single-board Linux system that began life as “Linux on a breadboard”. It’s a super-minimal Linux system containing only a 68K family CPU, 512K ROM, and 512K RAM. I began with a 16 year old Linux distro and hacked it to support this hardware and its tiny memory size. The original version was literally built on a breadboard, though the current version is now a PCB with a serial port for I/O.

During testing for the VCF show, I found that 68 Katy was no longer running reliably. I’d previously overclocked the 8 MHz-rated 68008 CPU to 12 MHz. Restoring an 8 MHz oscillator seemed to fix the problems – for now.

Nibbler – Another custom-made CPU and computer with a 4-bit (nibble) architecture. Designed to be simple to build and easy to understand, Nibbler’s CPU core consists of just 13 discrete 7400-series logic chips – individual counters, registers, buffers, and gates. To complete the machine, it adds a few ROMs and an SRAM, as well as pushbuttons, an audio speaker, and a text display. With a 4-bit CPU and 4K of memory you might think Nibbler couldn’t do anything much more interesting than blink an LED, but it boasts some nice games and demos. Like BMOW 1, it’s all hand wire-wrapped.

Nibbler will see a significant change for the VCF show, time permitting. The original design uses a 4K ROM for storing the program – when you want to run a different program, you need to replace the ROM. I plan to substitute a 16K ROM with a DIP switch to control the highest two address lines, so I can select between four different stored programs without resorting to ROM swapping.

Antique and Custom Computers Galore

Beyond the BMOW stuff, the other exhibits planned for VCF West XI look great! They include Eric Schlaepfer’s MonSter 6502, Bill Buzbee’s Magic-1, vintage DEC and Data General systems, IBM mainframes, Amigas, TRS-80s, S-100 hardware, and much more. Check out the full list here.

The show hours are 9:30-6:00 on Saturday the 6th and 9:00-5:30 on Sunday the 7th. Do you plan to attend? Leave a comment below, and I’ll keep an eye out for you!

Good news, ROM-heads! The software needed for ROM-inator II programming is now available for Mac OSX as well as Windows, and I’m marking the occasion with this step-by-step guide for creating your own bootable ROM disk. Here’s what you’ll need in order to get started:

Lastly, you’ll also need a disk image file that defines the contents of your ROM disk. If you’ve previously used a Floppy Emu disk emulator or a Macintosh software emulator like Mini vMac, you’ve doubtless seen these kinds of disk image files before. For ROM-inator II, the disk image file should be in “raw” format, meaning it contains only the actual contents of the Macintosh disk with no extra headers or checksums. Files in this format typically have a .dsk suffix for their filename. If in doubt, confirm that the first two bytes of the file are 4C 4B (hex). You’ll find an example disk image at the ROM-inator II project page.

Prepare the Disk Image

When using compression, the current model ROM-inator II SIMM can store a disk image as large as about 5.5 MB – the exact limit depends on the contents of the disk image and its compressibility. You can use your own pre-existing disk image, or start with this empty 5.5 MB disk image. If you’re using your own disk image, its size must be a multiple of 65536 bytes (64 KB).

I recommend Mini vMac for editing the contents of the disk image. It’s a cross-platform tool that emulates a Macintosh Plus, and you can quickly mount disk images by dragging them into the Mini vMac window. Once you’ve mounted a few different disk images, you can copy programs and data between images to configure your ROM disk image however you’d like it. If you’re unfamiliar with this process, check out this disk image setup tutorial for the original ROM-inator.

On Windows, another alternative is HFV Explorer to transfer data directly to/from the disk image, without a Mac emulation intermediary.

Don’t forget to include a System folder in your disk image! The Macintosh will need an operating system in order to boot. You can find installers for Systems 6 and 7 at Macintosh Garden – as well as all sorts of other vintage Mac software.

Compress the Disk Image

Next, you’ll compress the disk image file so that it fits in the space available in ROM. The compression format is FC8, a custom format that I designed specifically for this purpose. The FC8 compressor is a command line program, so you’ll need to run it from a command prompt (Windows) or terminal (Mac). The ROM-inator II disk driver uses FC8’s block compression format, with 65536 byte blocks. To compress the disk image, type this at the command line:

fc8.exe -b:65536 mydisk.dsk mydisk.fc8

This will compress the disk image file mydisk.dsk, and create the compressed file mydisk.fc8. If the fc8 program or the disk images aren’t in the current directory, you’ll need to specify the path to those files on the command line.

Check the size of the resulting mydisk.fc8 file. For the current model ROM-inator II SIMM, the compressed file must be no larger than 3.5 MB (3670016 bytes). If it’s too big, remove some files from your disk image and try again. Note that simply deleting a file from the disk image may not help, because “deleting” normally just marks sectors as unused but doesn’t actually set their contents to zero. To truly delete the file and gain better compression density, you may need to create a new disk image from scratch and then copy all the files from the old disk image. It’s a minor hassle, but worth it for the improved compression density. For reference, the example disk image compresses to 63% of its original size, when using FC8 65536 byte blocks.

Create the ROM Contents File

You’ll need to concatenate the 512K base ROM file and the compressed disk image file, in order to create the final ROM contents file. The base ROM file contains the low-level code needed to operate your Macintosh, including the ROM disk driver that performs on-the-fly decompression of your disk image’s data. At the time of writing this file is named iisi+romdrv1.2.rom, but check the project page to get the latest version. The concatenation is performed on the command line, using the built-in programs copy (Windows) or cat (Mac OSX and Linux):

copy /b iisi+romdrv1.2.rom + mydisk.fc8 myrom.rom (Windows)

cat iisi+romdrv1.2.rom mydisk.fc8 > myrom.rom (Mac OSX and Linux)

This will concatenate the files iisi+romdrv1.2.rom and mydisk.fc8, and create the combined file myrom.rom. If the files aren’t in the current directory, you’ll need to specify the path to those files on the command line.

The resulting myrom.rom file should be 4 MB (4194304 bytes) or less, in order to fit the space available in the current model ROM-inator II SIMM.

Program the SIMM

The final step is to program the ROM-inator II SIMM with your new ROM contents file. Connect your ROM SIMM Programmer to your PC or Mac’s USB port. Turn the programmer’s power switch to OFF, insert the ROM SIMM in the socket, then turn the switch to ON. Open the ROM SIMM programmer utility software.

From the software’s GUI, select myrom.rom as the file to write. Programming speed will be fastest when “verify after writing” is selected as the verification option. Ensure the SIMM capacity is set correctly (4 MB for the current model ROM-inator II SIMM), then press the Write to SIMM button.

After programming is complete, turn the programmer’s power switch to OFF, and then remove the ROM SIMM from the socket. Have fun with your new ROM disk!

This funny-looking device is a DC barrel plug to Apple IIc DIN-7 adapter, inspired by last week’s musings on constructing a battery-powered IIc. The adapter makes it possible to power an Apple IIc with a standard DC supply between 9V and 20V, or a suitable battery pack with a DC plug. The supply or battery should be capable of delivering at least 20 watts, or about 1.67 amps at 12V.

For my experiments, I used a Belkin BU3DC001-12V, which is essentially a fancy 12V 7.2Ah battery with built-in charging circuitry, output regulation circuitry, and fuse. It’s intended to be a backup battery for VOIP systems, but can easily be repurposed for any 12V DC application. Best of all, it’s only about $20 used, which is hardly more than the cost of the battery itself.

The current draw estimates from my earlier post proved to be about right. When running from the 12V battery, the IIc pulls about 1.5 amps for a few seconds while the floppy drive spins. Once the drive stops, the current drops down to about 700 mA. Given the 7.2 amp-hour capacity of the Belkin unit, that ought to be enough for several hours of battery-operated IIc fun.

Building your own DC to IIc adapter is simple, and only requires some wire and a few dollars in parts.

If you’re wondering why there’s no funny video here of a IIc running in the woods, it’s because I’ve only solved half the problem. A battery-powered IIc is pretty useless without a battery-powered monitor to use with it. Fortunately, 12V DC powered LCDs with a composite video input aren’t difficult to find. Many portable DVD players and car entertainment systems can do that job. To power it, I could build another custom cable to run the monitor and the Apple IIc off the Belkin battery, but I’m going to be lazy and simply buy this splitter:

It remains to be seen how much current the monitor will draw from the battery, but hopefully not much. I’ll report again when I have solid numbers.

While I already have a portable DVD player that will work here, its 5 inch diagonal is a little bit underwhelming. I also have a much nicer 14 inch LCD monitor that runs from 12V DC, but it only has a VGA input and no composite input. I’ll keep my eyes peeled for an LCD that’s 9 inches or larger, running from 12V DC, with a composite video input, to create the ultimate battery-powered Apple IIc system. Then I can… um… OK, I admit there’s no real point to this project.

The ROM-inator II replacement flash ROM for the Mac II series and SE/30 comes pre-programmed with nifty new features for your vintage Macintosh. With the optional ROM SIMM Programmer, you can edit the ROM’s contents, altering the ROM disk or writing a different stock ROM image. But why stop there? For the truly adventurous, this tutorial will demonstrate how to patch the ROM code to alter the machine’s low-level behaviors. This is an advanced tutorial for major gear-heads, so hang on to your hat!

We’ll begin with the Macintosh IIsi ROM. It’s a universal ROM, meaning that even though it was designed for the IIsi, it also works in many other Mac models. The original IIsi ROM is just a 512K chunk of raw data, which you can find here. The ROM-inator II’s contents are also based on the IIsi ROM, with many modifications and additions. The latest ROM-inator II contents are available on the product’s web page, and at the time of writing it’s this file. Only the first 512K of the file is ROM code, and the rest is data for the ROM disk.

Hex Editor

To modify or patch the file, we’ll need a tool called a hex editor. I’ll be using a Windows hex editor called xvi32, but there are many other options for Windows, Mac, and Linux. Check out Synalyze It and Hex Fiend for some other examples. If we open the ROM-inator II file in xvi32, we’ll see this:

What’s all this? Running down the left side are the file offsets in hex. These are the same as the addresses within the ROM code. In the center panel, we see the actual bytes from the file, displayed in hex, 16 bytes per line. In the right panel we see those same 16 bytes again, but displayed as printable characters instead of as hex values. That’s not especially useful in this example, but it’s handy when examining ROM code that contains embedded string constants.

In the example above, the value at offset 32 is 6E, which is equivalent to the ASCII character ‘n’.

Disassembler

To do anything useful with this, we’ll need to understand how these bytes are structured and what they mean, so that we’ll have some idea how to modify them. In this case, we know that the bytes are 68000 machine code, so we can feed them through a 68000 disassembler to create a more human-readable version. As with the hex editor, there are many options for 68K disassemblers, including this slick web-based disassembler. Using the web disassembler to examine the first few bytes of the file, we’ll get output like this:

Once again, the left column shows the file offsets (ROM addresses), and the center column displays the actual bytes in hex. The column on the right displays those same bytes reinterpreted as 68000 machine code. The number of bytes per row is no longer fixed at 16, but instead varies with the size of the encoded 68000 instructions. Notice that the code is displayed using syntax normally employed for x86 disassembly, so it looks a bit odd for those people accustomed to 68K syntax. But even if we ignore the syntax, something about this code just looks wrong. It begins with a couple of strange move instructions, a negation, and OR-ing random-seeming registers with strange constants. It just looks wrong, and that’s because it is wrong. One of the limitations of disassemblers is that they struggle to distinguish code from data, and in this example the bytes beginning at address zero are mostly data. By attempting to interpret them as 68K code, we get garbage.

By employing some knowledge about the 68K CPU, we can make better sense of this. At reset time, the 68K initializes its stack pointer from address 0, and its program counter from address 4, then it begins executing code. So the first instruction to be executed will be the one whose address appears at offset 4 in ROM, which we can see from the hex dump is 4080002A hex. That may seem like a strange address, since it’s a 32-bit address far outside the range of the 512K ROM code. Once again, we need to employ some knowledge of Macintosh internals to know that the ROM is initially mapped into the CPU’s address space at 40800000. So 4080002A simply means offset 2A in the ROM. As it turns out, the instruction at 2A was disassembled correctly in the listing above, and it’s just a PC-relative jump to address 8C. If we try the disassembler again, this time feeding in the bytes beginning at 8C and adjusting the base address accordingly in the disassembler settings, we get something that looks more reasonable:

It begins by loading a value into the status register, which the 68000 manual tells us will disable interrupts. It then loads a value into D0 and stores it into the cache control register. More processor initialization follows. Whew! We can make sense of this, but it’s slow and tedious work.

A Mac-Specific Disassembler

For this work, a better disassembler is FDisasm, a 68K disassmbler with some Mac-specific intelligence. FDisasm is itself a vintage Macintosh program running under System 6 or 7, rather than a modern Windows or OSX application, so it’s normally run under emulation with the cross-platform Mini vMac emulator. In addition to simply disassembling the 68K code, FDisasm also replaces address and data constant values with their symbolic names, where those names are known from Apple reference sources or previous disassembly work. It even inserts some helpful comments into the disassembled code. To do all this, FDisasm needs to have formatting information with advance knowledge of the Mac ROM being disassembled. Unfortunately, the IIsi isn’t one of the ROMs for which FDisasm contains pre-supplied formatting information. But happily for us, Rob Braun has already done some work in this area, and created partial formatting information for FDisasm with the IIsi ROM. Using that formatting information, FDisasm generates this disassembly beginning at address 8C:

That looks much better! We see that address 8C has the label StartBoot, and other addresses and constants also now have meaningful names. It looks like the MOVEC instruction was disassembled incorrectly (a FDisasm bug?), but that’s a small matter. With disassembly at this level, we can finally begin to search for interesting sections of code to study, and eventually to modify.

Double Chime

As an example, we’ll walk through the construction of a ROM patch to make the Mac play the startup chime twice. Maybe it’s such a great chime that it deserves to be played twice? Poking through the disassembly, we eventually find some relevant code at address 45C0A:

While it’s not obvious, I can tell you from super-secret sleuthing that this code is called from a computed jump instruction at 4651A:

This code requires some explanation. At the point the boot chime is played, the Mac’s RAM hasn’t yet been configured, and there is no stack. That means the code can’t use the normal JSR/RTS mechanism to call and return from subroutines. If we examine the code at OrigBootBeep6, we’ll learn that it uses the A6 register as a return address, once it’s done playing the chime. So the line above that loads DT140 into A6 is setting the return address, which happens to be the address of the instruction immediately following the jump. To play two chimes, we’ll need to duplicate this block of code two times.

Patching code becomes problematic when the new code requires more bytes than the old code. The code contains many address cross-references, so we can’t simply shift the bytes down to make room for new code, the way we’d insert an extra word into a sentence in a text editor. Instead we need to find some unused area of the ROM, put the new, larger code into that area, and then modify the original code to jump to the new code. Finding a suitable unused area is as much art as science, but while skimming through the ROM disassembly, this jumps out at address 3CBE:

I’m going to hazard a guess that somebody named “Gary” worked on the IIsi ROM.

Gary appears to have filled up padding space with many copies of his name, which we can replace with new code. If we’re wrong and all those “Gary” bytes are actually necessary, the computer will crash horribly. Such is the excitement of ROM hacking. We want to insert some new code that plays the chime twice, then jumps back to the instruction just after the old code. Using the original code as a template, our new code should look something like this:

where $XXXX and $YYYY are the offsets from HERE1 and HERE2 to OrigBootBeep6, and $ZZZZ is the offset from NEXT2 to DT140, the continuation point of the original code. We can compute those offsets by doing some hexadecimal math, subtracting the addresses where those instructions lie in the “Gary” area from the addresses we need to jump to. We’ll use the hex editor to do the actual patching work. Using xvi32 to view Gary’s ROM padding beginning at address 3CBE:

We can type directly into the center area of byte values to modify them. But what bytes should we type, to implement the new code that we want? Converting from assembly code to byte values is the job of an assembler, so we could use a 68K assembler like EASy68K to do the work. But in this case, almost all of the instructions already exist in the original code, so we can simply copy the assembled byte values from there, modifying the bytes that represent addresses as needed. For example, we can see from the original code that MoveQ.L $28, D0 assembles as the two bytes 70 28. Beginning with the first “Gary” at 3CC4, we’ll crib bytes from the original code, not yet worrying about the address offsets. The result looks like this:

The offsets require more careful study. First, we consider the instructions like Lea.L NEXT1, A6. While this looks like an absolute address, it’s actually a PC-relative address. Another FDisasm bug? An alternative 68K disassembler represents these same instructions as LEA ($C, PC), A6. This loads A6 with the address 10 bytes ($C hex) beyond the current program counter value. 10 is still the correct adjustment in our new code, so that doesn’t need to change. Next we consider the computed jump instructions like JMP HERE1(A0.L). While this looks like an absolute offset, it’s actually a PC-relative offset that the alternative disassembler shows as JMP (-$8, PC, A0.L). Once again, -$8 is also the correct adjustment in our new code, so that doesn’t need to change either.

The XXXX, YYYY, and ZZZZ offsets are the only values that need to change. In the original code, the instruction was:

46514 41F9 FFFF F6F6 DT139: LEA.L (-$90A), A0

46514 was the address, 41F9 was the instruction opcode, and FFFFF6F6 was the (negative) offset. So we need to find the three instances of the bytes FFFFF6F6 in the new code, and modify them to the correct offsets for OrigBootBeep6 (twice, from HERE1 and HERE2) and DT140. After applying some math, these offsets turn out to be 00003388, 00003378, and 0004283A, respectively.

Finally, we need to patch the original code, so that it jumps to the new code. To do this, we’ll perform a similar hex calculation to subtract the original code’s address from the “Gary” address at 3CC4. We only need to modify the offset in the instruction at address 46514 to point to our new code instead of directly to OrigBootBeep6. This is a little bit sloppy, as D0 and A6 will end up getting set redundantly, but it’s simpler than modifying that whole block of code at 4650E.

This should give you a sense of the kinds of ROM modifications that are possible with the ROM-inator II and the ROM SIMM programmer. Patching the ROM can be challenging work, but with a little imagination and patience almost anything is possible.