Serial Roundup

Serial communication between a computer an a microcontroller can be a great control/feedback/debugging tool, and at $0 dollars, is way cheaper than a JTAG interface! Unfortunately, configuring and debugging your serial setup can be a pain (and really, you shouldn’t have to debug your debugger), so I thought I would start a thread with my favorite (free) PC serial port tools. I hope other people will add to it, especially with tips and software for other operating systems, since for the moment, I do all my work in Windows.

Of course the biggest trick for Windows users is that you can reassign com port numbers from the device manager (right click on My Computer->Properties->Hardware tab->Device Manager). Open up the “Ports” list and double click on one you want to change, then go to the “Port Settings” tab and click on “Advanced…”. There you’ll see the “COM Port Number” drop down menu, which is exactly what it sounds like. You may need to do a little shuffling to exchange numbers between two ports, but don’t pay too much attention to the “(in use)” tag next to certain port numbers. If Windows assigned a port number to something you plugged in once long ago, like a USB to Serial adapter, it keeps that port reserved for all time. You can totally assign another port this number, you just have to click through a warning. It’s probably not a good idea to assign the same port number to two devices you’ll have plugged in at the same time though…

On to the list:

Br@y terminal
My absolute favorite terminal program. It’s a standalone executable, so you can carry it around on a thumb-drive, but it is incredibly full-featured and intuitive, with separate out and in windows, and all features accessible right from the main window (i.e. no navigating through ten menus to turn off flow control). Want to change the baud rate? One Click. Just hooked up a USB-Serial adapter? Click ‘Rescan’ and oh look there it is. Want to look at incoming bytes in HEX, ASCII, DEC, and Binary at the same time, while monitoring the handshaking pin states and logging to a file with a timestamp on every new line…okay, you get the picture.

Tips & Tricks:
*BE CAREFUL LOGGING BINARY DATA! The “RX Clear” character (default ESC 27) will clear the terminal screen AND flush the port’s receive FIFO, so any bytes in the FIFO after the clear character won’t end up in your log file. This has led me on several hours of wild goose chasing. Fortunately you can effectively disable the “RX Clear” option by setting the value to zero.
*You can ignore the error you see when you run multiple copies at once, it has to do with communication with remote clients, the local serial functions all still work fine.
*Try out all the buttons and check boxes. My favs are “ASCII Table” to bring up a built-in character table for quick reference, “Graph” for a graph function that plots incoming bytes in real time (i.e. sonar range, accelerometer readings, it rocks), and “Auto Dis/Connect” which will disconnect when the terminal isn’t the top window, then reconnect when it gets back on top.
*Type in the text bar to set up strings to be sent when you hit enter or click “Send”, or type directly into the output window to send characters out as you hit them.
*It supports some sort of scripting I haven’t needed to figured out, because it also has awesome programmable (and savable) macro buttons.
*You can send number-valued bytes (i.e. non-ASCII), just type ‘$’ before a two digit hex number, or ‘#’ before a three digit decimal number (you have to pad with zeros, or it won’t work quite right). So, for example: $46 = #070 = ‘F’, or if you wanted to tell a serial servo controller in Pololu mode to set servo 1 to position 3000 using absolute position command 4, you would write: $80$01$04#001#023#056 (the first three numbers are hex and the last three are dec).
*Click the “Help” button for a rundown of the rocking advanced features!

HHD Free Serial Port Monitor
It’s like wire-tapping your serial port, only it’s done entirely in software! Start this puppy up before your serial communicating program and set it to monitor the port you’ll be using, and you can see all the incoming and outgoing bytes in hex and ascii, and other nice things like the delays between outgoing and incoming bytes, and the state of the handshaking lines. I like the “Request View” window the best, but check them all out to start. The pay-version has more features, like a protocol analyzer and log file playback, but I’ve never really needed those.

Tips & Tricks:
*Once you’ve got a port/window setup you like, save the session, and load it up quickly later without having to reconfigure everything.
*Save the contents of your log windows to parse later.
*Don’t freak out when you don’t see incoming bytes. This isn’t a terminal, and it doesn’t read bytes in the receive buffer, so another program must be reading the incoming bytes for them to show up.
*Don’t worry too much about bytes showing up in big chunks after a short delay, I haven’t precisely measured it, but it doesn’t seem to show down the actual serial communication noticeably.

com0com virtual null modem
Tapping into a real serial port is nice, but it doesn’t let you send bytes to your program so you can watch the response they get. This open source tool from SourceForge (yay) lets you create pairs of virtual serial ports connected by a virtual standard (hah!) null-modem cable, or an arbitrary one you design. These pairs of ports show up as a new category of device in the device manager, so some programs will not recognize them as com ports (VSA for one), but most seem to.

Tips & Tricks:
*Test out any program involving serial communication by connecting it to one virtual serial port, and a terminal program to the other (duh).
*Work on your serial programs on computers with no serial ports!
*Give your ports normal port names (i.e. “COM1”) so they’ll be recognized by more programs.
*If it tells you a com port is “In Use” (when it really isn’t) when you try to change the name of a virtual port just hit “Continue”.
*Skip the “Launch Setup Command Prompt” option at the end of the install, this puppy has a GUI configuration utility called “Setup” in the program folder (with drag & drop wiring!):

Windows Serial Port Programming by Robertson Bayer
I appreciate that Microsoft is trying to maintain backwards compatibility, but the Windows API can be quite intimidating. This document explains everything you need to know to do basic serial communication in Windows from a C or C++ program (and maybe other languages?). It covers configuring and opening a port, sending and receiving data, and closing the port when you’re done, all with copy-paste-able code examples. It’s the basis for all the serial communication programs I have ever written, like this one for Pololu serial servo control.

Tips & Tricks:
*Don’t forget to #include windows.h, which is only mentioned once in the document and not shown in any of the code examples!
*PC UARTs have huge buffers, so don’t worry about reading in bytes right on time, but also be aware that they might build up. If I’m expecting a quick response from a command sometimes I’ll try to read 100 bytes from a com port just to make sure the buffer is clear before sending the command out. It sounds to me like the “FlushFileBuffers” command should do this, but sadly it doesn’t work that way.
*The default timeouts are fine for “hit a key to move a servo” type programs, but they’re a little long for auto-communication between two devices. If I know when I’m expecting responses I usually turn them down to:


If I really need to keep things fast I turn the timeout multipliers to 1 as well, and retry a few times if I don’t get back the bytes I’m expecting.
*The MSDN library article with the advanced DCB settings mentioned in the document is here. It’s got some useful settings like setting up hardware flow control.

That’s the list so far, but I hope it will keep growing!


Wow, thanks for the great resource, Adam!

- Ben

Update: The instructions in the Windows Serial Port Programming document will work fine, but only for ports com1 through com9. You can access any Windows com port (including com1-com9) by simply changing the file string:

hSerial = CreateFile("COMn", GENERIC_READ | GENERIC_WRITE, 0, 0, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);//works for com1-com9
hSerial = CreateFile("\\\\.\\COMn", GENERIC_READ | GENERIC_WRITE, 0, 0, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);//works for any com port

In the code snippets above, hSerial is a handle, and “n” is a placeholder for the com port number.