HOWTO: Debugging for Newbies

This is the nth in a series of tutorials I don't have time to write, really. So it will be little more than a sketch. But I'm tired of telling this story in person, so I'd like to point people here first. Here's how to debug…

A) Prepare for debugging

  1. Make sure your code is ready to debug.
  2. Get in a reasonable debugging environment.

B) Characterize the failure.

  1. Can you set up the program to repeatedly fail? What is the minimum input needed to do this? Can you cut the program down to something simple that fails (without too much work)? Take notes.
  2. Stop the program in the debugger at (or if possible before) points of potential failure. Step through the program, noting the state and how it changes. Take notes.

C) Determine the root cause of the failure.

  1. Develop some hypotheses (note plural) as to the proximate causes of the observed failures (the defects or "bugs"). Take notes.
  2. For each hypothesis in turn, develop and apply experimental tests that will confirm or deny the hypothesis. This may involve modifying the program, using the debugger, running the program with different data, etc. Take notes.
  3. Once the bugs are adequately characterized, identify causes for the bug to get into the code (the root causes of the errors or "mistakes"). These may range from inadequate documentation of infrastructure to poor typing skills to sleepiness to whatever. Take notes.
  4. Put steps in place to remedy the root causes of the errors.
  5. For each error, identify other bugs introduced as a result of that error, and fix those also. Take notes.

D) Exercise the program carefully to make sure it has been debugged. Save all tests that failed before and pass now as "regression tests" to check that the bug doesn't return in the future.


When debugging:

  1. Don't get stuck. If you have pursued a given approach for 5 or 10 minutes without success, make a note and then abandon it temporarily. Banging harder typically won't budge it.
  2. Ask for help. Debugging is a good team activity.
  3. Take frequent breaks. Keep sessions short. Don't get sleepy; go to bed and try again in the morning. Remember that forcing it never works.
  4. Keep referring to your notebook. It tells the story of what you've tried, and what you still want to try.
  5. Use plenty of assertions. Don't remove them when debugging is complete (unless absolutely necessary for performance or correctness).
  6. Specific tools you should master in the Linux command line environment: gcc -Wall -g, gdb, valgrind.
  7. Don't get stuck. Take notes.

Hope this helps.