16.4. termios Debugging
Debugging tty code is not always easy. The options overlap in meaning and affect each other in various ways, often in ways that you do not intend. But you cannot easily see what is happening with only a debugger, because the processing that you are trying to manage is happening in the kernel.
One effective way to debug code that communicates over a serial port is to use the script program. While developing robin, we connected two computers with a serial cable and verified that the connection worked by running the already-working kermit program. While still running kermit on the local computer, we ran the script program on the remote computer, which started keeping a log of all the characters in the file typescript. Then we quit kermit and ran script on the local computer, which put a typescript file in the current directory on the local computer. We then tried to run robin under script and compared the two typescript files at each end after each run to see the differences in characters. We thereby deciphered the effects of the processing options we had chosen.
Another debugging method takes advantage of the stty program. If, while you are testing a program, you think you recognize a mistake in the termios settings, you can use the stty program to make the change immediately rather than recompile your program first. If you are working on /dev/ttyS0, and you want to set the ECHOCTL flag, simply run the command
stty echoctl < /dev/ttyS0
while your program is running.
Similarly, you can view the current status of the port you are using with
stty -a < /dev/ttyS0
As we explained before, it is hard to use the same tty for running the debugger and for running the tty-mangling program you are debugging.
Instead, you want to attach to the process. This is not difficult to do. In one X-terminal session (do this under X so that you can see both ttys at once), run the program you want to debug. If you need to, put a long sleep() in it at the point at which you wish to attach to it:
$ ./robin -b 38400 /dev/ttyS1
Now, from another X-terminal session, find the pid of the program you are trying to debug, in one of two ways:
$ ps | grep robin 30483 ? S 0:00 ./robin -b 38400 /dev/ttyS1 30485 ? S 0:00 grep robin $ pidof robin 30483
pidof is more convenient, but may not be available on every system. Keep the number you found (here, 30483) in mind and start a debugging session the same way you normally would.
$ gdb robin 30483 GDB is free software... ... Attaching to program '.../robin', process 30483 Reading symbols from ... 0x40075d88 in sigsuspend ()
From this point, you can set breakpoints and watchpoints, step through the program, or whatever you like.