Debugging by using remote debuggers in Linux projects

Start Your Application Now Debugging consumes the lion's share of time in a project. Peeling away the wrapper around programming methodology fads usually exposes methods and practices for minimizing the time spent debugging, us...
This article was sent to us by: Jules Fabiane at 02012010

1 Software » Debugging by using remote debuggers in Linux projects
Bookmark and Share

Start Your Application Now

Debugging consumes the lion's share of time in a project. Peeling away the wrapper around programming methodology fads usually exposes methods and practices for minimizing the time spent debugging, usually via planning and adding help during the debugging phase. Part of this article is dedicated to practices that reduce debugging, but mostly it focuses on tools to use when you're debugging. The information is mixed, because it's sometimes difficult to separate one topic from the other. This article covers debugging both C/C++ and Java programs in detail, using remote debuggers. Engineering projects using these languages do a fair amount of debugging remotely, and knowing how to get this debugging setup running is an important part of the project. As you've seen so far with Linux, there are at least three different ways to do everything, and debugging provides more of the same. The techniques for instrumentation transcend language; they just have implementation differences. Embedded engineers fall back on instrumentation because you can't find defects that are timing related by stepping through the code. Even though remote debugging technologies have improved vastly over the years, the favorite debugging tool for embedded engineers remains printf().

Types of Debugging

There are a few different ways to look at application debugging: interactive, post mortem, and instrumentation. This article focuses on the first and last debugging types with the most detail, because they're the most commonly used and productive techniques. Due to the space limitations on embedded systems, getting a core dump for post-mortem debugging isn't that common, but the concept does merit mention for systems that are less memory constrained. Following are descriptions of the three approaches:

The goal of debugging is, of course, to root out problems. However, many times engineers use debugging as a learning aid. No matter how well the documentation describes how a function call works, being able to see the results first hand and perhaps change the parameters interactively is a great technique for those who learn by experimentation. All of these debugging methods are well-supported in Linux.

Remote Debugging Overview

Debugging when the debugger and the program being debugged run on separate hosts is called remote debugging. Whereas regular debugging involves two major components (the debugger and the program being debugged), remote debugging adds one more item to the list: the debug monitor. The debug monitor is a stand-in for the debugger that's running on a different machine; during debugging, the debugger and the monitor exchange messages over a communications link, and the monitor handles the mechanics of settings the breakpoints and fetching the contents of memory when you ask to see a variable's value. When you use the GNU debugger (which is really the only C/C++ debugger for Linux), the debug monitor is gdbserver. For a Java program, the debug monitor is built into the virtual machine: when you run the program with the java executable, you pass in a few extra parameters. The way Java is structured, debugging on the machine where the program is running and from a remote machine use nearly the same communication mechanism.

Debugging C and C++

In order to debug C and C++ code, you must compile the code with debugging information. On a Linux system, that debugging information is in DWARF 2 format, the successor to the original Debugging With Attributed Record Formats (DWARF)2. DWARF 2 describes a format for storing information about line numbers and symbols as additional data in the file. With this information, a debugger can understand how the data is stored in memory and has an idea of what instructions belong with one line. When the code is compiled correctly, if it's to be debugged remotely, two programs are necessary: the debugger (GDB) and the debug monitor (gdbserver) The GDB binary runs on your development host computer, and gdbserver runs on the target. The rationale for having two programs is simple: gdbserver is much smaller and requires very few resources in order to work, whereas GDB needs quite a bit of memory, which the target machine may lack. If you're using a toolchain built with crosstool-ng, you can find the gdbserver component at /debug-root/usr/bin/gdbserver. This program is linked without shared library dependencies, so all you need to do is copy it to the /bin directory of the target system.

Legal Disclaimer

Our website is not responsible for the information contained by this article. Articleinput.com is a free articles resource thus practically any visitor can submit an article. However if you notice any copyrighted material, please contact us and we will remove the article(s) in discussion right away.

Related Articles

1. Embedded Linux is used for some very good commercial reasons
Commercial Reasons to Use Embedded Linux In addition to the outstanding technical aspects of Linux that make it advantageous to use for an embedded device, ther...

2. Linux and its memory management system
Memory Management and Linux Linux uses a virtual memory-management system. The concept of virtual memory has been around since the early 1960s and is simple: th...

3. Why is Linux such an incredible piece of sowtware
Embedded Linux Linux is an incredible piece of software. It’s an operating system that’s just as at home running on IBM’s zSeries supercompute...

4. Explanation of the Embedded Linux development process
Embedded Linux is a topic with many interdependencies; this article lays out the big points and purposely lacks detail so you can see the big picture without getting dist...

5. Basics to understanding the structure of an embedded Linux system
Anatomy of an Embedded Linux System At runtime, an embedded Linux system contains the following software components: • Boot loader: What gets the ope...

6. The resemblance between the GCC compiler and the kernel in Linux
The GNU Compiler Collection The GCC compiler, like the kernel, is designed for portability. Like all open source programs, GCC is available in source form, and ...

7. Automake and Autoconf discover the state of the target environment
Automake/Autoconf Open source software is designed to be distributed in source code form so that it can be compiled for the target platform. When target platfor...