• Articles
  • Debugging using gdb: Find a segFault
Published by
Aug 15, 2012 (last update: Aug 15, 2012)

Debugging using gdb: Find a segFault

Score: 3.9/5 (229 votes)
*****
To get started with gdb, short examples are good. Once you know how to run it (gdb nameOfProgram), how to examine and traverse the stack (bt, up, down), see the code you're currently in (list) and how to get the values of variables (print) you're equipped to deal with the most common crashes (i.e. segFaults) and you've bootstrapped yourself to the point that you can learn more yourself.

Here's a sample session:

1
2
3
4
5
6
7
8
9
10
11
12
#include<iostream>
using namespace std;

int main()
{

  int x = 7;
  int *p = 0;

  cout << "x = " << x;
  cout << "The pointer points to the value " << *p;
}


Wrote some code, now I'll build it and run. What I type is in bold, what's on the screen is in italics.

j@j-desktop:~/badCode$ g++ 227.cpp
j@j-desktop:~/badCode$ ./a.out
Segmentation fault

Oh no, a segfault. I'll rebuild it with debugging symbols and then run it under the debugger.

j@j-desktop:~/badCode$ g++ -g 227.cpp
j@j-desktop:~/badCode$ gdb ./a.out
GNU gdb (GDB) 7.1-ubuntu
Copyright (C) 2010 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "x86_64-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>...
Reading symbols from /home/j/badCode/a.out...done.
(gdb)
run
Starting program: /home/j/badCode/a.out

Program received signal SIGSEGV, Segmentation fault.
0x0000000000400824 in main () at 227.cpp:13
13 cout << "The pointer points to the value " << *p;



Thoughts: Well, the segFault happens on this line. I'm using a pointer here, p. I'd better check the value of that pointer.

(gdb) print p
$1 = (int *) 0x0
Thoughts:Aha! The pointer has a value of zero - it's a null pointer. Trying to dereference it is causing a segFault. Let's see the nearby code.

(gdb) list
int x = 7;
int *p = 0;

cout << "x = " << x;
cout << "The pointer points to the value " << *p;
}




Thoughts: Ah, I never set the pointer to point at anything. That's easily fixed.

(gdb) quit A debugging session is active.

Inferior 1 [process 6779] will be killed.

Quit anyway? (y or n)


Fix the code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include<iostream>

using namespace std;

int main()
{

  int x = 7;
  int *p = 0;
  p = &x;

  cout << "x = " << x;
  cout << "The pointer points to the value " << *p;
}


Now build and run:
j@j-desktop:~/badCode$ g++ 227.cpp
j@j-desktop:~/badCode$ ./a.out
x = 7The pointer points to the value 7

So there we have it. The commands I used were:

gdb ./a.out - Start gdb attached to the program I'm interested in. This does not start the program running.
run - Start program running
print p - Show me the value of the object named p.
list - Show the line that execution has paused at, and surrounding lines of code.
quit - Exit gdb.

I suggest you do something similar yourself to practice a little. SegFaults are wonderfully easy to track down like this. Literally thirty seconds with gdb can identify the exact problem. I've seen people spend hours trying to do it by hand, staring at the code, printlining variables all over the place, just because they didn't want to get into the debugger.