Here’s a tip for anyone building a device designed to interface with a parallel printer – you kind of need a parallel printer to test it on.
That shouldn’t have been a problem. My DottyMatrix project – which will allow me to send data over a serial connection and have it printed on my Epson MX-80 F/T III dot matrix printer – was conceived precisely because I want to use the printer that I’ve had lying about the place for the past three decades or so.
Except that the printer doesn’t work. Not right now, anyway.
The current state of the project is this:
I have the parallel breakout board I built as part of learning Eagle and KiCad. In its current state, this isn’t much more than a handy way of mounting a shift register and wiring it to a DB25 connector.
I’ve written code, first for the ATMEGA328P and now adapted for the ATMEGA328PB. This takes data coming in on a serial connection and sends the right signals over the parallel port. It puts the data bytes on the eight data lines using the shift register and also controls the /STROBE and /INIT outputs (going to the printer) and monitors the BUSY, /ACK and /ERROR signals coming from the printer. (Other signal lines, such as ‘paper out’ haven’t been implemented yet. Some will be, some won’t.)
It all works as far as I can test it. But in the current code, I’m simply entering short delays to simulate, say, the printer being busy printing a character. I have put in routines to test for time-outs in certain circumstances, but have no way of knowing if those are working as advertised. To test the timeouts I need to connect to an external device that does, or doesn’t, send back the expected signals in time.
So what do I do if the printer isn’t working? Simulate one!
So here’s the plan: I’m using an ATMEGA328P as my printer.
I have a 74HC541 buffer to manage incoming and outgoing signals. The incoming signals (aside from the eight data lines) are /STROBE and /INIT. I’ve configured these as interrupts on the microcontroller, triggering on falling edges – more on this in the next post. The outgoing signals are BUSY, /ACK and /ERROR.
A 74HC165 parallel-to-serial shift register acts as a buffer for the data lines. I’ve also added an eight-segment bar LED unit to show what’s on the data lines.
The code is pretty simple. It sits in a loop waiting for a pulse on either /STROBE or /INIT. If it gets an ‘init’ signal, it asserts the BUSY line, pauses for a moment to simulate the printer initialising, then drops the BUSY line again and goes back to the loop. I’ve put an LED on the BUSY line for visual confirmation.
If there’s a pulse on /STROBE, the program asserts the BUSY line, sends a low pulse on the /ACK line, reads in the eight bits from the shift register, pauses for a moment to simulate printing the character then drops the BUSY line and goes back to the loop.
The Epson MX-80 F/T III wasn’t the world’s faster printer. I have a hazy recollection of its speed being measured in ‘characters per fortnight’. Actually, looking online I find that the Epson was rated at 80 characters per second in normal print mode. That’s 12.5ms per character, so I’m using something like that for the ‘printing’ delay.
I’ve also added a serial port so that I can send various monitoring and debugging messages to a serial terminal along with the ‘printed’ text.
I can now play with delays and pulse timings to see if the timeouts in the DottyMatrix code are working.
Once I’m happy the virtual printer is functioning as it should be, I can remove all the bogus delays from DottyMatrix that were simulating printer activity and focus on producing the real code for the final device.
I’m thinking I might actually build this virtual printer as a PCB, in which case the signal lines will be buffered via a 74HC541. I’ll also add the ‘paper out’ (PE) and AUTOFEED signal lines. As a product, its market is probably very small (ie, me) but it’ll be fun and good practice. Here’s the current state of the schematic.